package com.xuan.bazi.core;

import com.nlf.calendar.EightChar;
import com.nlf.calendar.Lunar;
import com.nlf.calendar.Solar;
import com.nlf.calendar.eightchar.*;
import com.xuan.bazi.core.constant.Constant;
import com.xuan.bazi.utils.CommonUtil;
import com.xuan.bazi.utils.DateUtil;
import lombok.Getter;

import java.util.*;

/**
 * 八字
 *
 * @author kty
 */
//@Data
@Getter
public class BaZi {

    /**
     * 农历日期
     */
    private Lunar lunar;
    /**
     * 公历日期
     */
    private Solar solar;
    /**
     * 农历日期
     */
    private String lunarStr;
    /**
     * 公历日期
     */
    private String solarStr;
    /**
     * 星期
     */
    private String week;

    /**
     * 年干
     */
    private String yearGan;
    /**
     * 月干
     */
    private String monthGan;
    /**
     * 日干
     */
    private String dayGan;
    /**
     * 时干
     */
    private String hourGan;

    /**
     * 年支
     */
    private String yearZhi;
    /**
     * 月支
     */
    private String monthZhi;
    /**
     * 日支
     */
    private String dayZhi;
    /**
     * 时支
     */
    private String hourZhi;

    /**
     * 年柱
     */
    private String yearZhu;
    /**
     * 月柱
     */
    private String monthZhu;
    /**
     * 日柱
     */
    private String dayZhu;
    /**
     * 时柱
     */
    private String hourZhu;

    /**
     * 年干五行
     */
    private String yearGanWuXing;
    /**
     * 月干五行
     */
    private String monthGanWuXing;
    /**
     * 日干五行
     */
    private String dayGanWuXing;
    /**
     * 时干五行
     */
    private String hourGanWuXing;

    /**
     * 年支五行
     */
    private String yearZhiWuXing;
    /**
     * 月支五行
     */
    private String monthZhiWuXing;
    /**
     * 日支五行
     */
    private String dayZhiWuXing;
    /**
     * 时支五行
     */
    private String hourZhiWuXing;

    /**
     * 年柱五行
     */
    private String yearZhuWuXing;
    /**
     * 月柱五行
     */
    private String monthZhuWuXing;
    /**
     * 日柱五行
     */
    private String dayZhuWuXing;
    /**
     * 时柱五行
     */
    private String hourZhuWuXing;

    /**
     * 年柱纳音
     */
    private String yearZhuNaYin;
    /**
     * 月柱纳音
     */
    private String monthZhuNaYin;
    /**
     * 日柱纳音
     */
    private String dayZhuNaYin;
    /**
     * 时柱纳音
     */
    private String hourZhuNaYin;

    /**
     * 年柱空亡
     */
    private String yearZhuKongWang;
    /**
     * 月柱空亡
     */
    private String monthZhuKongWang;
    /**
     * 日柱空亡
     */
    private String dayZhuKongWang;
    /**
     * 时柱空亡
     */
    private String hourZhuKongWang;

    /**
     * 八字
     */
    private List<String> baZi;
    /**
     * 八字五行
     */
    private List<String> baZiWuXing;
    /**
     * 八字纳音
     */
    private List<String> baZiNaYin;
    /**
     * 八字空亡
     */
    private List<String> baZiKongWang;

    /**
     * 年柱主星（如：正财）
     */
    private String yearZhuZhuXing;
    /**
     * 月柱主星（如：正财）
     */
    private String monthZhuZhuXing;
    /**
     * 日柱主星（如：元男）
     */
    private String dayZhuZhuXing;
    /**
     * 时柱主星（如：正财）
     */
    private String hourZhuZhuXing;

    /**
     * 年支藏干（如：子水）
     */
    private List<String> yearZhiCangGan;
    /**
     * 月支藏干（如：子水）
     */
    private List<String> monthZhiCangGan;
    /**
     * 日支藏干（如：子水）
     */
    private List<String> dayZhiCangGan;
    /**
     * 时支藏干（如：子水）
     */
    private List<String> hourZhiCangGan;

    /**
     * 年柱副星（如：正财）
     */
    private List<String> yearZhuFuXing;
    /**
     * 月柱副星（如：正财）
     */
    private List<String> monthZhuFuXing;
    /**
     * 日柱副星（如：正财）
     */
    private List<String> dayZhuFuXing;
    /**
     * 时柱副星（如：正财）
     */
    private List<String> hourZhuFuXing;

    /**
     * 年柱地势
     */
    private String yearZhuDiShi;
    /**
     * 月柱地势
     */
    private String monthZhuDiShi;
    /**
     * 日柱地势
     */
    private String dayZhuDiShi;
    /**
     * 时柱地势
     */
    private String hourZhuDiShi;

    /**
     * 八字五行得失（如：五行齐全）
     */
    private List<String> baZiWuXingDeShi;
    /**
     * 八字五行格局（如：2木 1火 2土 2金 1水）
     */
    private List<String> baZiWuXingGeJu;
    /**
     * 身体强弱（如：身强）
     */
    private String bodyIntensity;
    /**
     * 喜用神（如：木）
     */
    private List<String> xiYongShen;
    /**
     * 喜用神方位（如：北）
     */
    private List<String> xiYongShenFangWei;

    /**
     * 胎元
     */
    private String taiYuan;
    /**
     * 胎息
     */
    private String taiXi;
    /**
     * 命宫
     */
    private String mingGong;
    /**
     * 身宫
     */
    private String shenGong;
    /**
     * 起运
     */
    private String qiYun;

    /**
     * 大运
     */
    private List<Object> daYun;
    /**
     * 小运
     */
    private List<Object> xiaoYun;
    /**
     * 流年
     */
    private List<Object> liuNian;
    /**
     * 流月
     */
    private List<Object> liuYue;

    /**
     * 年柱神煞
     */
    private List<String> yearZhuShenSha;
    /**
     * 月柱神煞
     */
    private List<String> monthZhuShenSha;
    /**
     * 日柱神煞
     */
    private List<String> dayZhuShenSha;
    /**
     * 时柱神煞
     */
    private List<String> hourZhuShenSha;

//****************************************************************************************************************************************************

    /**
     * 使用默认设置计算（默认使用当前公历日期）
     */
    public BaZi() {
        setDate(new BaZiSetting()); // ★获取并设置数据
    }

    /**
     * 使用公历日期初始化
     *
     * @param date 公历日期（如：2023-01-01-06-00-00）
     */
    public BaZi(String date) {
        BaZiSetting setting = new BaZiSetting();
        setting.setDate(DateUtil.stringToDate(date, DateUtil.DATE_TIME_FORMAT_2));
        setDate(setting); // ★获取并设置数据
    }

    /**
     * 使用日期初始化
     *
     * @param date     日期（如：2023-01-01-06-00-00）
     * @param dateType 日期类型（0:公历，1:农历）
     */
    public BaZi(String date, int dateType) {
        BaZiSetting setting = new BaZiSetting();
        setting.setDate(DateUtil.stringToDate(date, DateUtil.DATE_TIME_FORMAT_2));
        setting.setDateType(dateType);
        setDate(setting); // ★获取并设置数据
    }

    /**
     * 使用自定义设置初始化（若未设置日期则默认使用当前公历日期）
     *
     * @param setting 八字设置
     */
    public BaZi(BaZiSetting setting) {
        setDate(setting); // ★获取并设置数据
    }

//====================================================================================================================================================

    /**
     * ★获取并设置数据
     *
     * @param setting 八字设置
     */
    private void setDate(BaZiSetting setting) {

        // 初始化自定义数据
        initializeBaZiSetting(setting);

        // 计算数据
        baZiInfo(); // 计算八字五行、八字纳音、八字空亡
        zhuXing(setting); // 计算主星
        diZhiCangGan(); // 计算地支藏干
        fuXing(); // 计算副星
        baZiDiShi(setting); // 计算八字地势
        taiGong(setting); // 计算胎元、胎息、命宫、身宫
        qiYun(setting); // 计算起运
        baZiWuXingDeShi(); // 计算八字五行得失（如：五行齐全）
        baZiWuXingGeJu(); // 计算八字五行格局（如：2木 1火 2土 2金 1水）
        bodyIntensity(); // 计算身体强弱（如：身强）
        xiYongShen(); // 计算喜用神
        xiYongShenFangWei(); // 计算喜用神方位
        shenSha(setting); // 计算并封装四柱神煞
        DaYun[] daYun = daYun(setting);// 计算大运
        xiaoYun(daYun); // 计算小运
        LiuNian[] liuNian = liuNian(daYun);// 计算流年
        liuYue(liuNian); // 计算流月

        System.gc();

    }

    /**
     * 初始化自定义数据
     *
     * @param setting 八字设置
     */
    private void initializeBaZiSetting(BaZiSetting setting) {

        // 1、数据校验
        int dateType = setting.getDateType(); // 日期类型（0:公历，1:农历）
        if (dateType != BaZiEnum.DATE_TYPE_SOLAR.getMark() && dateType != BaZiEnum.DATE_TYPE_LUNAR.getMark()) {
            setting.setDateType(BaZiEnum.DATE_TYPE_SOLAR.getMark());
        }

        // 2、☆判断日期类型并返回农历日期、公历日期
        Map<String, Object> map = BaZiUtil.isDateType(setting);

        // 3、设置日期
        this.lunar = (Lunar) map.get("lunar"); // 农历日期
        this.solar = (Solar) map.get("solar"); // 公历日期
        this.lunarStr = (String) map.get("lunarStr"); // 农历日期
        this.solarStr = (String) map.get("solarStr"); // 公历日期

        // 4、设置星期
        this.week = "周" + getLunar().getWeekInChinese();

        // 5、☆判断四柱设置并返回八字
        this.baZi = BaZiUtil.isSiZhu(setting, getLunar());
        this.yearZhu = getBaZi().get(0); // 年柱
        this.monthZhu = getBaZi().get(1); // 月柱
        this.dayZhu = getBaZi().get(2); // 日柱
        this.hourZhu = getBaZi().get(3); // 时柱
        this.yearGan = getYearZhu().substring(0, 1); // 年干
        this.monthGan = getMonthZhu().substring(0, 1); // 月干
        this.dayGan = getDayZhu().substring(0, 1); // 日干
        this.hourGan = getHourZhu().substring(0, 1); // 时干
        this.yearZhi = getYearZhu().substring(1, 2); // 年支
        this.monthZhi = getMonthZhu().substring(1, 2); // 月支
        this.dayZhi = getDayZhu().substring(1, 2); // 日支
        this.hourZhi = getHourZhu().substring(1, 2); // 时支

    }

    /**
     * 计算八字五行、八字纳音、八字空亡
     */
    private void baZiInfo() {

        EightChar ec = getLunar().getEightChar();

        // 1、设置八字五行
        this.yearZhuWuXing = ec.getYearWuXing(); // 年柱五行
        this.monthZhuWuXing = ec.getMonthWuXing(); // 月柱五行
        this.dayZhuWuXing = ec.getDayWuXing(); // 日柱五行
        this.hourZhuWuXing = ec.getTimeWuXing(); // 时柱五行
        this.yearGanWuXing = getYearZhuWuXing().substring(0, 1); // 年干五行
        this.monthGanWuXing = getMonthZhuWuXing().substring(0, 1); // 月干五行
        this.dayGanWuXing = getDayZhuWuXing().substring(0, 1); // 日干五行
        this.hourGanWuXing = getHourZhuWuXing().substring(0, 1); // 时干五行
        this.yearZhiWuXing = getYearZhuWuXing().substring(1, 2); // 年支五行
        this.monthZhiWuXing = getMonthZhuWuXing().substring(1, 2); // 月支五行
        this.dayZhiWuXing = getDayZhuWuXing().substring(1, 2); // 日支五行
        this.hourZhiWuXing = getHourZhuWuXing().substring(1, 2); // 时支五行
        this.baZiWuXing = Arrays.asList(ec.getYearWuXing(), ec.getMonthWuXing(), ec.getDayWuXing(), ec.getTimeWuXing()); // 八字五行

        // 2、设置八字纳音
        this.yearZhuNaYin = ec.getYearNaYin(); // 年柱纳音
        this.monthZhuNaYin = ec.getMonthNaYin(); // 月柱纳音
        this.dayZhuNaYin = ec.getDayNaYin(); // 日柱纳音
        this.hourZhuNaYin = ec.getTimeNaYin(); // 时柱纳音
        this.baZiNaYin = Arrays.asList(ec.getYearNaYin(), ec.getMonthNaYin(), ec.getDayNaYin(), ec.getTimeNaYin()); // 八字纳音

        // 3、设置八字空亡
        this.yearZhuKongWang = ec.getYearXunKong(); // 年柱空亡
        this.monthZhuKongWang = ec.getMonthXunKong(); // 月柱空亡
        this.dayZhuKongWang = ec.getDayXunKong(); // 日柱空亡
        this.hourZhuKongWang = ec.getTimeXunKong(); // 时柱空亡
        this.baZiKongWang = Arrays.asList(ec.getYearXunKong(), ec.getMonthXunKong(), ec.getDayXunKong(), ec.getTimeXunKong()); // 八字空亡

    }

    /**
     * 计算主星
     *
     * @param setting 八字设置
     */
    private void zhuXing(BaZiSetting setting) {

        /*
            根据日干与年干、月干、时干得出
         */

        Map<List<String>, String> zhuFuXing = BaZiMap.ZHU_FU_XING; // 主星与副星

        this.yearZhuZhuXing = zhuFuXing.get(CommonUtil.addList(getDayGan(), getYearGan())); // 年柱主星
        this.monthZhuZhuXing = zhuFuXing.get(CommonUtil.addList(getDayGan(), getMonthGan())); // 月柱主星
        // 性别判断
        if (setting.getSex() == BaZiEnum.SEX_MAN.getMark()) {
            this.dayZhuZhuXing = "元" + BaZiEnum.SEX_MAN.getDescribe(); // 元男
        } else if (setting.getSex() == BaZiEnum.SEX_WOMAN.getMark()) {
            this.dayZhuZhuXing = "元" + BaZiEnum.SEX_WOMAN.getDescribe(); // 元女
        }
        this.hourZhuZhuXing = zhuFuXing.get(CommonUtil.addList(getDayGan(), getHourGan())); // 时柱主星

    }

    /**
     * 计算地支藏干
     */
    private void diZhiCangGan() {

        Map<String, List<String>> diZhiCangGan = BaZiMap.DI_ZHI_CANG_GAN; // 地支藏干

        this.yearZhiCangGan = diZhiCangGan.get(getYearZhi()); // 年支藏干
        this.monthZhiCangGan = diZhiCangGan.get(getMonthZhi()); // 月支藏干
        this.dayZhiCangGan = diZhiCangGan.get(getDayZhi()); // 日支藏干
        this.hourZhiCangGan = diZhiCangGan.get(getHourZhi()); // 时支藏干

    }

    /**
     * 计算副星
     */
    private void fuXing() {

        /*
            根据日干与年支藏干、月支藏干、日支藏干、时支藏干得出
         */

        Map<List<String>, String> zhuFuXing = BaZiMap.ZHU_FU_XING; // 主星与副星

        // 1、计算年柱副星
        List<String> yearZhuFuXing = new ArrayList<>();
        List<String> yearZhiCangGan = getYearZhiCangGan(); // 年支藏干
        for (String item : yearZhiCangGan) {
            yearZhuFuXing.add(zhuFuXing.get(CommonUtil.addList(getDayGan(), item.substring(0, 1))));
        }

        // 2、计算月柱副星
        List<String> monthZhuFuXing = new ArrayList<>();
        List<String> monthZhiCangGan = getMonthZhiCangGan(); // 月支藏干
        for (String item : monthZhiCangGan) {
            monthZhuFuXing.add(zhuFuXing.get(CommonUtil.addList(getDayGan(), item.substring(0, 1))));
        }

        // 3、计算日柱副星
        List<String> dayZhuFuXing = new ArrayList<>();
        List<String> dayZhiCangGan = getDayZhiCangGan(); // 日支藏干
        for (String item : dayZhiCangGan) {
            dayZhuFuXing.add(zhuFuXing.get(CommonUtil.addList(getDayGan(), item.substring(0, 1))));
        }

        // 4、计算时柱副星
        List<String> hourZhuFuXing = new ArrayList<>();
        List<String> hourZhiCangGan = getHourZhiCangGan(); // 时支藏干
        for (String item : hourZhiCangGan) {
            hourZhuFuXing.add(zhuFuXing.get(CommonUtil.addList(getDayGan(), item.substring(0, 1))));
        }

        this.yearZhuFuXing = yearZhuFuXing;
        this.monthZhuFuXing = monthZhuFuXing;
        this.dayZhuFuXing = dayZhuFuXing;
        this.hourZhuFuXing = hourZhuFuXing;

    }

    /**
     * 计算八字地势
     *
     * @param setting 八字设置
     */
    private void baZiDiShi(BaZiSetting setting) {

        EightChar eightChar = getLunar().getEightChar();
        eightChar.setSect(setting.getZiShiLiuPai()); // 设置子时流派（0:晚子时日柱按明天，1:晚子时日柱按当天）

        this.yearZhuDiShi = eightChar.getYearDiShi(); // 年柱地势
        this.monthZhuDiShi = eightChar.getMonthDiShi(); // 月柱地势
        this.dayZhuDiShi = eightChar.getDayDiShi(); // 日柱地势
        this.hourZhuDiShi = eightChar.getTimeDiShi(); // 时柱地势

    }

    /**
     * 计算胎元、胎息、命宫、身宫
     */
    private void taiGong(BaZiSetting setting) {

        EightChar eightChar = getLunar().getEightChar();
        eightChar.setSect(setting.getZiShiLiuPai()); // 设置子时流派（0:晚子时日柱按明天，1:晚子时日柱按当天）

        this.taiYuan = eightChar.getTaiYuan() + "（" + eightChar.getTaiYuanNaYin() + "）"; // 胎元
        this.taiXi = eightChar.getTaiXi() + "（" + eightChar.getTaiXiNaYin() + "）"; // 胎息
        this.mingGong = eightChar.getMingGong() + "（" + eightChar.getMingGongNaYin() + "）"; // 命宫
        this.shenGong = eightChar.getShenGong() + "（" + eightChar.getShenGongNaYin() + "）"; // 身宫

    }

    /**
     * 计算起运
     *
     * @param setting 八字设置
     */
    private void qiYun(BaZiSetting setting) {

        EightChar eightChar = getLunar().getEightChar();
        eightChar.setSect(setting.getZiShiLiuPai()); // 设置子时流派（0:晚子时日柱按明天，1:晚子时日柱按当天）

        // 初始化运（设置性别、起运流派）
        Yun yun = eightChar.getYun(setting.getSex(), setting.getQiYunLiuPai() + 1);

        String qiYun = "出生";
        if (yun.getStartYear() != 0) qiYun += yun.getStartYear() + "年";
        if (yun.getStartMonth() != 0) qiYun += yun.getStartMonth() + "个月";
        if (yun.getStartDay() != 0) qiYun += yun.getStartDay() + "天";
        if (yun.getStartHour() != 0) qiYun += yun.getStartHour() + "分钟";
        qiYun += "后开始起运，起运时间(公历)：" + yun.getStartSolar().toYmdHms();

        this.qiYun = qiYun;

    }

    /**
     * 计算八字五行得失（如：五行齐全）
     */
    private void baZiWuXingDeShi() {

        Map<String, String> ganWuXing = BaZiMap.GAN_WU_XING; // 天干五行
        Map<String, String> zhiWuXing = BaZiMap.ZHI_WU_XING; // 地支五行

        // 1、添加八字五行数据
        Set<String> set = new HashSet<>(); // 保存八字五行（保证五行唯一性）
        set.add(ganWuXing.get(getYearGan())); // 年干五行
        set.add(ganWuXing.get(getMonthGan())); // 月干五行
        set.add(ganWuXing.get(getDayGan())); // 日干五行
        set.add(ganWuXing.get(getHourGan())); // 时干五行
        set.add(zhiWuXing.get(getYearZhi())); // 年支五行
        set.add(zhiWuXing.get(getMonthZhi())); // 月支五行
        set.add(zhiWuXing.get(getDayZhi())); // 日支五行
        set.add(zhiWuXing.get(getHourZhi())); // 时支五行
        List<String> list = new ArrayList<>(set); // set转list

        // 2、判断五行是否齐全
        List<String> baZiWuXingDeShi = new ArrayList<>(); // 保存五行状态
        if (list.size() == 5) {
            baZiWuXingDeShi.add(Constant.WU_XING_ALL);
            this.baZiWuXingDeShi = baZiWuXingDeShi;
            return;
        }


        // 3.1、初始化五行
        List<String> wuXingList = Arrays.asList(Constant.MU, Constant.HUO, Constant.TU, Constant.JIN, Constant.SHUI);
        // 3.2、添加八字中缺失的五行
        baZiWuXingDeShi = CommonUtil.getListUnlike(list, wuXingList);

        this.baZiWuXingDeShi = baZiWuXingDeShi;

    }

    /**
     * 计算八字五行格局（如：二木 二火 二土 二金 二水）
     */
    private void baZiWuXingGeJu() {

        // 1.1、添加干支五行
        List<String> ganZHiWuXingList = Arrays.asList(
                getYearGanWuXing(), getMonthGanWuXing(), getDayGanWuXing(), getHourGanWuXing(),
                getYearZhiWuXing(), getMonthZhiWuXing(), getDayZhiWuXing(), getHourZhiWuXing()
        );
        // 1.2、获取八字五行中出现的重复元素及出现次数
        Map<String, Integer> map = CommonUtil.getListIdentical(ganZHiWuXingList);

        // 2、保存五行格局数据
        List<String> baZiWuXingGeJu = new ArrayList<>();
        for (String key : map.keySet()) {
            baZiWuXingGeJu.add(map.get(key) + key);
        }

        this.baZiWuXingGeJu = baZiWuXingGeJu;

    }

    /**
     * 计算身体强弱（如：身强）
     * <p>
     * TODO：此处只采用[日元]和[月令]之间的五行生克关系、[日元]和[其他干支]进行判断，暂不考虑其他因素。
     */
    private void bodyIntensity() {

        /*
            ★判断方法：

                1、根据[日元]和[月令]之间的五行生克关系判断（日元:日天干，月令:月地支）
                    ①解释：日元代表自己，月令代表父母或兄弟。
                    ②口诀：同我、生我为强；克我、我生、我克为弱。（不代表最终的判断结果）

         */

        // 1、初始化干支
        List<String> ganZhi = Arrays.asList(getDayGan(), getMonthZhi());

        // 2、获取身体强弱
        this.bodyIntensity = BaZiMap.GAN_ZHI_WU_XING_SHENG_KE.get(ganZhi).get(0);

        // 3、获取身体强弱，根据算分再次判断（如：接近平衡）
        bodyIntensityConfirm();

    }

    /**
     * 计算身体强弱，根据算分再次判断（如：接近平衡）
     */
    private void bodyIntensityConfirm() {

        Map<List<String>, List<String>> ganGanShengKe = BaZiMap.GAN_GAN_WU_XING_SHENG_KE; // 天干和天干的[五行生克]
        Map<List<String>, List<String>> ganZhiShengKe = BaZiMap.GAN_ZHI_WU_XING_SHENG_KE; // 天干和地支的[五行生克]

        int jia = 0; // 加分（得分）
        int jian; // 减分（得分）

        // 1.1、通过日元（日干）与年干的五行生克关系算出加分
        jia += jiaFen(ganGanShengKe, getDayGan(), getYearGan(), 8); // 年干统一给8分
        // 1.2、通过日元（日干）与年支的五行生克关系算出加分
        jia += jiaFen(ganZhiShengKe, getDayGan(), getYearZhi(), 4); // 年支统一给4分
        // 1.3、通过日元（日干）与月干的五行生克关系算出加分
        jia += jiaFen(ganGanShengKe, getDayGan(), getMonthGan(), 12); // 月干统一给12分
        // 1.4、通过日元（日干）与月支的五行生克关系算出加分
        jia += jiaFen(ganZhiShengKe, getDayGan(), getMonthZhi(), 40); // 月支统一给40分
        // 1.5、通过日元（日干）与日支的五行生克关系算出加分
        jia += jiaFen(ganZhiShengKe, getDayGan(), getDayZhi(), 12); // 日支统一给12分
        // 1.6、通过日元（日干）与时干的五行生克关系算出加分
        jia += jiaFen(ganGanShengKe, getDayGan(), getHourGan(), 12); // 时干统一给12分
        // 1.7、通过日元（日干）与时支的五行生克关系算出加分
        jia += jiaFen(ganZhiShengKe, getDayGan(), getHourZhi(), 12); // 时支统一给12分

        jian = -(100 - jia); // 减分

        // 2.1、若加分等于50，则身体为：平衡（中庸之道）
        if (jia == 50 || jian == -50) {
            this.bodyIntensity = Constant.PING_HENG; // 平衡
            return;
        }
        // 2.2、若加分>=40并且<=60，则身体为：接近平衡（中庸之道）
        if ((jia >= 40 && jia <= 60) || (jian >= -60 && jian <= -40)) {
            this.bodyIntensity = Constant.NEAR_PING_HENG; // 接近平衡
        }

    }

    /**
     * 计算喜用神
     */
    private void xiYongShen() {

        Map<String, String> ganWuXing = BaZiMap.GAN_WU_XING; // 天干五行
        Map<String, String> zhiWuXing = BaZiMap.ZHI_WU_XING; // 地支五行
        Map<List<String>, List<String>> ganGanShengKe = BaZiMap.GAN_GAN_WU_XING_SHENG_KE; // 天干和天干的[五行生克]
        Map<List<String>, List<String>> ganZhiShengKe = BaZiMap.GAN_ZHI_WU_XING_SHENG_KE; // 天干和地支的[五行生克]

        // 1、若身体为[平衡]或[接近平衡]，则无需找喜用神
        if (getBodyIntensity().equals(Constant.PING_HENG) || getBodyIntensity().equals(Constant.NEAR_PING_HENG)) {
            List<String> list = new ArrayList<>();
            list.add("");
            this.xiYongShen = list;
            return;
        }

        Set<String> set = new HashSet<>();

        // 2、若身体为[强]，则寻找：克我、我生、我克的干支
        if (getBodyIntensity().equals(Constant.QIANG)) {
            // 2.1、判断日元（日干）与年干的五行生克关系
            if (!qiangOrRuo(ganGanShengKe, getDayGan(), getYearGan())) set.add(ganWuXing.get(getYearGan())); // 添加年干的五行
            // 2.2、判断日元（日干）与年支的五行生克关系
            if (!qiangOrRuo(ganZhiShengKe, getDayGan(), getYearZhi())) set.add(zhiWuXing.get(getYearZhi())); // 添加年支的五行
            // 2.3、判断日元（日干）与月干的五行生克关系
            if (!qiangOrRuo(ganGanShengKe, getDayGan(), getMonthGan())) set.add(ganWuXing.get(getMonthGan())); // 添加月干的五行
            // 2.4、判断日元（日干）与月支的五行生克关系
            if (!qiangOrRuo(ganZhiShengKe, getDayGan(), getMonthZhi())) set.add(zhiWuXing.get(getMonthZhi())); // 添加月支的五行
            // 2.5、判断日元（日干）与日支的五行生克关系
            if (!qiangOrRuo(ganZhiShengKe, getDayGan(), getDayZhi())) set.add(zhiWuXing.get(getDayZhi())); // 添加日支的五行
            // 2.6、判断日元（日干）与时干的五行生克关系
            if (!qiangOrRuo(ganGanShengKe, getDayGan(), getHourGan())) set.add(ganWuXing.get(getHourGan())); // 添加时干的五行
            // 2.7、判断日元（日干）与时支的五行生克关系
            if (!qiangOrRuo(ganZhiShengKe, getDayGan(), getHourZhi())) set.add(zhiWuXing.get(getHourZhi())); // 添加时支的五行
            this.xiYongShen = new ArrayList<>(set);
            return;
        }

        // 3、若身体为[弱]，则寻找：同我、生我的干支
        if (getBodyIntensity().equals(Constant.RUO)) {
            // 2.1、判断日元（日干）与年干的五行生克关系
            if (qiangOrRuo(ganGanShengKe, getDayGan(), getYearGan())) set.add(ganWuXing.get(getYearGan())); // 添加年干的五行
            // 2.2、判断日元（日干）与年支的五行生克关系
            if (qiangOrRuo(ganZhiShengKe, getDayGan(), getYearZhi())) set.add(zhiWuXing.get(getYearZhi())); // 添加年支的五行
            // 2.3、判断日元（日干）与月干的五行生克关系
            if (qiangOrRuo(ganGanShengKe, getDayGan(), getMonthGan())) set.add(ganWuXing.get(getMonthGan())); // 添加月干的五行
            // 2.4、判断日元（日干）与月支的五行生克关系
            if (qiangOrRuo(ganZhiShengKe, getDayGan(), getMonthZhi())) set.add(zhiWuXing.get(getMonthZhi())); // 添加月支的五行
            // 2.5、判断日元（日干）与日支的五行生克关系
            if (qiangOrRuo(ganZhiShengKe, getDayGan(), getDayZhi())) set.add(zhiWuXing.get(getDayZhi())); // 添加日支的五行
            // 2.6、判断日元（日干）与时干的五行生克关系
            if (qiangOrRuo(ganGanShengKe, getDayGan(), getHourGan())) set.add(ganWuXing.get(getHourGan())); // 添加时干的五行
            // 2.7、判断日元（日干）与时支的五行生克关系
            if (qiangOrRuo(ganZhiShengKe, getDayGan(), getHourZhi())) set.add(zhiWuXing.get(getHourZhi())); // 添加时支的五行
            this.xiYongShen = new ArrayList<>(set);
        }

    }

    /**
     * 计算喜用神方位
     */
    private void xiYongShenFangWei() {

        Map<String, List<String>> wuXingFangWei = BaZiMap.WU_XING_FANG_WEI; // 五行对应方位

        List<String> list = new ArrayList<>(); // 保存喜用神方位

        // 1、若身体为[平衡]或[接近平衡]，则无需找喜用神方位
        if (getBodyIntensity().equals(Constant.PING_HENG) || getBodyIntensity().equals(Constant.NEAR_PING_HENG)) {
            list.add("");
            this.xiYongShenFangWei = list;
            return;
        }

        // 2、获取喜用神方位
        for (int i = 0; i < getXiYongShen().size(); i++) {
            // 1.1、取出每一个喜用神的方位集合
            String xiYongShen = getXiYongShen().get(i);
            List<String> xiYongFangWei = wuXingFangWei.get(xiYongShen);
            // 1.2、保存所有喜用神的方位
            list.addAll(xiYongFangWei);
        }

        this.xiYongShenFangWei = list;

    }

    /**
     * 计算大运
     *
     * @param setting 八字设置
     */
    private DaYun[] daYun(BaZiSetting setting) {

        EightChar eightChar = getLunar().getEightChar();
        eightChar.setSect(setting.getZiShiLiuPai()); // 设置子时流派（0:晚子时日柱按明天，1:晚子时日柱按当天）

        // 初始化运【性别（0:女，1:男）。起运流派（0:按天数和时辰数计算：3天1年、1天4个月、1时辰10天，1:按分钟数计算：4320分=1年、360分=1月、12分=1天、1分=2小时）】
        Yun yun = eightChar.getYun(setting.getSex(), setting.getQiYunLiuPai());

        List<Object> daYunList = new ArrayList<>(); // 保存大运

        // 获取10轮大运
        DaYun[] daYun = yun.getDaYun(10);
        for (DaYun dy : daYun) {
            daYunList.add(new ArrayList<>(Arrays.asList(dy.getStartYear(), dy.getStartAge(), dy.getGanZhi())));
        }

        this.daYun = daYunList;

        return daYun;

    }

    /**
     * 计算小运
     *
     * @param daYun 大运
     */
    private void xiaoYun(DaYun[] daYun) {

        List<Object> xiaoYunList = new ArrayList<>(); // 保存小运

        // 遍历大运
        for (DaYun dy : daYun) {
            // 获取10轮小运
            XiaoYun[] xiaoYun = dy.getXiaoYun(10);
            for (XiaoYun xy : xiaoYun) {
                xiaoYunList.add(new ArrayList<>(Arrays.asList(xy.getYear(), xy.getAge(), xy.getGanZhi())));
            }
        }

        this.xiaoYun = xiaoYunList;

    }

    /**
     * 计算流年
     *
     * @param daYun 大运
     */
    private LiuNian[] liuNian(DaYun[] daYun) {

        List<Object> liuNianList = new ArrayList<>(); // 保存流年

        LiuNian[] liuNian = new LiuNian[]{};

        // 遍历大运
        for (DaYun dy : daYun) {
            // 获取10轮流年
            liuNian = dy.getLiuNian(10);
            for (LiuNian ln : liuNian) {
                liuNianList.add(new ArrayList<>(Arrays.asList(ln.getYear(), ln.getAge(), ln.getGanZhi())));
            }
        }

        this.liuNian = liuNianList;

        return liuNian;

    }

    /**
     * 计算流月
     *
     * @param liuNian 流年
     */
    private void liuYue(LiuNian[] liuNian) {

        List<Object> liuYueList = new ArrayList<>(); // 保存流月

        // 遍历流年
        for (LiuNian ln : liuNian) {
            // 获取流月
            LiuYue[] liuYue = ln.getLiuYue();
            for (LiuYue ly : liuYue) {
                liuYueList.add(new ArrayList<>(Arrays.asList(ly.getMonthInChinese() + "月", ly.getGanZhi())));
            }
        }

        this.liuYue = liuYueList;

    }

    /**
     * ★计算并封装四柱神煞（TODO：测试中）
     *
     * @param setting 八字设置
     */
    private void shenSha(BaZiSetting setting) {

        // 1、初始化数据集合
        List<String> yearShenSha = new ArrayList<>(); // 保存年柱神煞
        List<String> monthShenSha = new ArrayList<>(); // 保存月柱神煞
        List<String> dayShenSha = new ArrayList<>(); // 保存日柱神煞
        List<String> hourShenSha = new ArrayList<>(); // 保存时柱神煞

        // 2、添加数据
        saveShenShaZhi(tianDeGuiRen(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 天德贵人
        saveShenShaZhi(yueDeGuiRen(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 月德贵人
        saveShenShaZhi(deXiuGuiRen(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 德秀贵人
        saveShenShaZhi(sanQiGuiRen(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 三奇贵人
        saveShenShaZhi(tongZiSha(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 童子煞
        saveShenShaZhi(siFei(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 四废
        saveShenShaZhi(gongLu(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 拱禄
        saveShenShaZhi(tianShe(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 天赦
        saveShenShaZhi(tianZhuan(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 天转
        saveShenShaZhi(diZhuan(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 地转
        saveShenShaZhi(taiJiGuiRen(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 太极贵人【1】
        saveShenShaZhi(tianYiGuiRen(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 天乙贵人【1】
        saveShenShaZhi(fuXingGuiRen(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 福星贵人【1】
        saveShenShaZhi(wenChangGuiRen(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 文昌贵人【2】
        saveShenShaZhi(tianChuGuiRen(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 天厨贵人【2】
        saveShenShaZhi(guoYin(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 国印【2】
        saveShenShaZhi(yiMa(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 驿马【2】
        saveShenShaZhi(huaGai(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 华盖【2】
        saveShenShaZhi(jieSha(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 劫煞【2】
        saveShenShaZhi(jiangXing(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 将星【2】
        saveShenShaZhi(taoHua(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 桃花【2】
        saveShenShaZhi(wangShen(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 亡神【2】
        saveShenShaZhi(sangMen(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 丧门【2】
        saveShenShaZhi(diaoKe(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 吊客【2】
        saveShenShaZhi(piMa(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 披麻【2】
        saveShenShaZhi(yinChaYangCuo(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 阴差阳错【3】
        saveShenShaZhi(shiEDaBai(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 十恶大败【3】
        saveShenShaZhi(guLuanSha(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 孤鸾煞【3】
        saveShenShaZhi(kuiGang(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 魁罡【3】
        saveShenShaZhi(baZhuan(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 八专【3】
        saveShenShaZhi(jiuChou(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 九丑【3】
        saveShenShaZhi(shiLing(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 十灵【3】
        saveShenShaZhi(liuXiu(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 六秀【3】
        saveShenShaZhi(xueTang(setting.getXueTangSet()), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 学堂【4】
        saveShenShaZhi(ciGuan(setting.getCiGuanSet()), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 词馆【4】
        saveShenShaZhi(hongYanSha(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 红艳煞【5】
        saveShenShaZhi(jinYu(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 金舆【5】
        saveShenShaZhi(yangRen(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 羊刃【5】
        saveShenShaZhi(feiRen(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 飞刃【5】
        saveShenShaZhi(xueRen(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 血刃【5】
        saveShenShaZhi(liuXia(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 流霞【5】
        saveShenShaZhi(tianYi(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 天医【5】
        saveShenShaZhi(tianXi(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 天喜【5】
        saveShenShaZhi(hongLuan(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 红鸾【5】
        saveShenShaZhi(zaiSha(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 灾煞【5】
        saveShenShaZhi(guChen(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 孤辰【5】
        saveShenShaZhi(suGua(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 寡宿【5】
        saveShenShaZhi(luShen(), yearShenSha, monthShenSha, dayShenSha, hourShenSha); // 禄神【5】

        // 3、删除list集合中的空元素
        CommonUtil.removeListNull(yearShenSha, "");
        CommonUtil.removeListNull(monthShenSha, "");
        CommonUtil.removeListNull(dayShenSha, "");
        CommonUtil.removeListNull(hourShenSha, "");

        // 4、设置数据
        this.yearZhuShenSha = yearShenSha;
        this.monthZhuShenSha = monthShenSha;
        this.dayZhuShenSha = dayShenSha;
        this.hourZhuShenSha = hourShenSha;

    }

    /**
     * ☆计算并返回天德贵人
     *
     * @return 四柱神煞：天德贵人
     */
    private List<String> tianDeGuiRen() {

        /*
            【天德贵人】算法↓

                1、月支是子，并且其他天干或地支有'巳'的，则为天德贵人；
                2、月支是丑，并且其他天干或地支有'庚'的，则为天德贵人；
                3、月支是寅，并且其他天干或地支有'丁'的，则为天德贵人；
                4、月支是卯，并且其他天干或地支有'申'的，则为天德贵人；
                5、月支是辰，并且其他天干或地支有'壬'的，则为天德贵人；
                6、月支是巳，并且其他天干或地支有'辛'的，则为天德贵人；
                7、月支是午，并且其他天干或地支有'亥'的，则为天德贵人；
                8、月支是未，并且其他天干或地支有'甲'的，则为天德贵人；
                9、月支是申，并且其他天干或地支有'癸'的，则为天德贵人；
                10、月支是酉，并且其他天干或地支有'寅'的，则为天德贵人；
                11、月支是戌，并且其他天干或地支有'丙'的，则为天德贵人；
                12、月支是亥，并且其他天干或地支有'乙'的，则为天德贵人。
         */

        List<String> list = CommonUtil.addNullList(4);

        String _tianDeGanZhi = BaZiMap.TIAN_DE_GUI_REN.get(getMonthZhi()); // 根据月支获取天德贵人落入的天干或地支

        // 1、判断年柱
        if (getYearGan().equals(_tianDeGanZhi) || getYearZhi().equals(_tianDeGanZhi)) {
            list.set(0, Constant.TIAN_DE_GUI_REN);
        }

        // 2、判断月柱
        if (getMonthGan().equals(_tianDeGanZhi) || getMonthZhi().equals(_tianDeGanZhi)) {
            list.set(1, Constant.TIAN_DE_GUI_REN);
        }

        // 3、判断日柱
        if (getDayGan().equals(_tianDeGanZhi) || getDayZhi().equals(_tianDeGanZhi)) {
            list.set(2, Constant.TIAN_DE_GUI_REN);
        }

        // 4、判断时柱
        if (getHourGan().equals(_tianDeGanZhi) || getHourZhi().equals(_tianDeGanZhi)) {
            list.set(3, Constant.TIAN_DE_GUI_REN);
        }

        return list;

    }

    /**
     * ☆计算并返回月德贵人
     *
     * @return 四柱神煞：月德贵人
     */
    private List<String> yueDeGuiRen() {

        /*
            【月德贵人】算法↓

                1、月支是申、子、辰，并且其他天干是'壬'的，则为月德贵人。
                2、月支是寅、午、戌，并且其他天干是'丙'的，则为月德贵人。
                3、月支是亥、卯、未，并且其他天干是'甲'的，则为月德贵人。
                4、月支是巳、酉、丑，并且其他天干是'庚'的，则为月德贵人。
         */

        List<String> list = CommonUtil.addNullList(4);

        String _yueDeGan = BaZiMap.YUE_DE_GUI_REN.get(getMonthZhi()); // 根据月支获取月德贵人落入的天干

        // 1、判断年柱
        if (getYearGan().equals(_yueDeGan)) {
            list.set(0, Constant.YUE_DE_GUI_REN);
        }

        // 2、判断月柱
        if (getMonthGan().equals(_yueDeGan)) {
            list.set(1, Constant.YUE_DE_GUI_REN);
        }

        // 3、判断日柱
        if (getDayGan().equals(_yueDeGan)) {
            list.set(2, Constant.YUE_DE_GUI_REN);
        }

        // 4、判断时柱
        if (getHourGan().equals(_yueDeGan)) {
            list.set(3, Constant.YUE_DE_GUI_REN);
        }

        return list;

    }

    /**
     * ☆计算并返回德秀贵人
     *
     * @return 四柱神煞：德秀贵人
     */
    private List<String> deXiuGuiRen() {

        /*
            【德秀贵人】算法↓

                1、月支是子，并且其他天干有'戊'或者'己'或者'壬'或者'癸'的，则为德秀贵人。
                2、月支是丑，并且其他天干有'庚'或者'辛'的，则为德秀贵人。
                3、月支是寅，并且其他天干有'丙'或者'丁'的，则为德秀贵人。
                4、月支是卯，并且其他天干有'甲'或者'乙'的，则为德秀贵人。
                5、月支是辰，并且其他天干有'戊'或者'己'或者'壬'或者'癸'的，则为德秀贵人。
                6、月支是巳，并且其他天干有'庚'或者'辛'的，则为德秀贵人。
                7、月支是午，并且其他天干有'丙'或者'丁'的，则为德秀贵人。
                8、月支是未，并且其他天干有'甲'或者'乙'的，则为德秀贵人。
                9、月支是申，并且其他天干有'戊'或者'己'或者'壬'或者'癸'的，则为德秀贵人。
                10、月支是酉，并且其他天干有'庚'或者'辛'的，则为德秀贵人。
                11、月支是戌，并且其他天干有'丙'或者'丁'的，则为德秀贵人。
                12、月支是亥，并且其他天干有'甲'或者'乙'的，则为德秀贵人。
         */

        List<String> list = CommonUtil.addNullList(4);

        List<String> _deXiuGuiRenZhi = BaZiMap.DE_XIU_GUI_REN.get(getMonthZhi()); // 根据月支获取德秀贵人落入的地支

        for (String s : _deXiuGuiRenZhi) {
            // 1、判断年柱
            if (s.equals(getYearGan())) {
                list.set(0, Constant.DE_XIU_GUI_REN);
            }

            // 2、判断月柱
            if (s.equals(getMonthGan())) {
                list.set(1, Constant.DE_XIU_GUI_REN);
            }

            // 3、判断日柱
            if (s.equals(getDayGan())) {
                list.set(2, Constant.DE_XIU_GUI_REN);
            }

            // 4、判断时柱
            if (s.equals(getHourGan())) {
                list.set(3, Constant.DE_XIU_GUI_REN);
            }
        }

        return list;

    }

    /**
     * ☆计算并返回三奇贵人
     *
     * @return 四柱神煞：三奇贵人
     */
    private List<String> sanQiGuiRen() {

        /*
            【三奇贵人】算法↓

                天上三奇甲戊庚；地上三奇乙丙丁；人中三奇壬癸辛。三奇不管顺逆，只要连续有三个天干相连，即可入格，重逢则更贵。
         */

        String[] sanQiGuiRen = BaZiMap.SAN_QI_GUI_REN; // 三奇贵人

        List<String> list = CommonUtil.addNullList(4); // 保存四柱中的三奇贵人

        String ymdS = getYearGan() + getMonthGan() + getDayGan(); // 获取年月日天干
        String ymdN = getDayGan() + getMonthGan() + getYearGan(); // 获取日月年天干
        String mdhS = getMonthGan() + getDayGan() + getHourGan(); // 获取月日时天干
        String mdhN = getHourGan() + getDayGan() + getMonthGan(); // 获取时日月天干

        //1、判断年干、月干、日干、时干是否构成三奇贵人
        for (String sqgr : sanQiGuiRen) {
            if (ymdS.equals(sqgr) || ymdN.equals(sqgr)) {
                list.set(0, Constant.SAN_QI_GUI_REN); // 添加年柱神煞
                list.set(1, Constant.SAN_QI_GUI_REN); // 添加月柱神煞
                list.set(2, Constant.SAN_QI_GUI_REN); // 添加日柱神煞
            }
            if (mdhS.equals(sqgr) || mdhN.equals(sqgr)) {
                list.set(1, Constant.SAN_QI_GUI_REN); // 添加月柱神煞
                list.set(2, Constant.SAN_QI_GUI_REN); // 添加日柱神煞
                list.set(3, Constant.SAN_QI_GUI_REN); // 添加时柱神煞
            }
        }

        return list;

    }

    /**
     * ☆计算并返回童子煞
     *
     * @return 四柱神煞：童子煞
     */
    private List<String> tongZiSha() {

        /*
            【童子煞】算法↓

                1、春秋寅子贵：春天和秋天出生的，日支或时支有'寅'或者'子'为童子煞。
                2、冬夏卯未辰：冬天和夏天出生的，日支或时支有'卯'或者'未'或者'辰'为童子煞。
                3、金木午卯合：年命属金或木，日支或时支有'午'或者'卯'为童子煞。
                4、水火酉戍多：年命属水或火，日支或时支有'酉'或者'戍'为童子煞。
                5、土命逢辰巳：年命属土，日支或时支有'辰''或者'巳'为童子煞。
         */

        List<String> list = CommonUtil.addNullList(4);

        String season = getLunar().getSeason().substring(1, 2); // 获取季节简称（如：春）
        String yearMingWuXing = getYearZhuNaYin().substring(2, 3); // 年命五行

        // 1、春秋寅子贵：春天和秋天出生的，日支或时支有'寅'或者'子'为童子煞。
        if (Constant.CHUN_SEASON.equals(season) || Constant.QIU_SEASON.equals(season)) {
            if (Constant.YIN_ZHI.equals(getDayZhi()) || Constant.ZI_ZHI.equals(getDayZhi())) list.set(2, Constant.TONG_ZI_SHA);
            if (Constant.YIN_ZHI.equals(getHourZhi()) || Constant.ZI_ZHI.equals(getHourZhi())) list.set(3, Constant.TONG_ZI_SHA);
        }

        // 2、冬夏卯未辰：冬天和夏天出生的，日支或时支有'卯'或者'未'或者'辰'为童子煞。
        if (Constant.DONG_SEASON.equals(season) || Constant.XIA_SEASON.equals(season)) {
            if (Constant.MAO_ZHI.equals(getDayZhi()) || Constant.WEI_ZHI.equals(getDayZhi()) || Constant.CHEN_ZHI.equals(getDayZhi())) list.set(2, Constant.TONG_ZI_SHA);
            if (Constant.MAO_ZHI.equals(getHourZhi()) || Constant.WEI_ZHI.equals(getHourZhi()) || Constant.CHEN_ZHI.equals(getDayZhi())) list.set(3, Constant.TONG_ZI_SHA);
        }

        // 3、金木午卯合：年命属金或木，日支或时支有'午'或者'卯'为童子煞。
        if (Constant.JIN.equals(yearMingWuXing) || Constant.MU.equals(yearMingWuXing)) {
            if (Constant.WU_ZHI.equals(getDayZhi()) || Constant.MAO_ZHI.equals(getDayZhi())) list.set(2, Constant.TONG_ZI_SHA);
            if (Constant.WU_ZHI.equals(getHourZhi()) || Constant.MAO_ZHI.equals(getHourZhi())) list.set(3, Constant.TONG_ZI_SHA);
        }

        // 4、水火酉戍多：年命属水或火，日支或时支有'酉'或者'戍'为童子煞。
        if (Constant.SHUI.equals(yearMingWuXing) || Constant.HUO.equals(yearMingWuXing)) {
            if (Constant.YOU_ZHI.equals(getDayZhi()) || Constant.XU_ZHI.equals(getDayZhi())) list.set(2, Constant.TONG_ZI_SHA);
            if (Constant.YOU_ZHI.equals(getHourZhi()) || Constant.XU_ZHI.equals(getHourZhi())) list.set(3, Constant.TONG_ZI_SHA);
        }

        // 5、土命逢辰巳：年命属土，日支或时支有'辰''或者'巳'为童子煞。
        if (Constant.TU.equals(yearMingWuXing)) {
            if (Constant.CHEN_ZHI.equals(getDayZhi()) || Constant.SI_ZHI.equals(getDayZhi())) list.set(2, Constant.TONG_ZI_SHA);
            if (Constant.CHEN_ZHI.equals(getHourZhi()) || Constant.SI_ZHI.equals(getHourZhi())) list.set(3, Constant.TONG_ZI_SHA);
        }

        return list;

    }

    /**
     * ☆计算并返回四废
     *
     * @return 四柱神煞：四废
     */
    private List<String> siFei() {

        /*
            【四废】算法↓

                1、春季出生：日柱是'庚申'或者'辛酉'的，为四废。
                2、夏季出生：日柱是'壬子'或者'癸亥'的，为四废。
                3、秋季出生：日柱是'甲寅'或者'乙卯'的，为四废。
                4、冬季出生：日柱是'丁巳'或者'丙午'的，为四废。
         */

        List<String> list = CommonUtil.addNullList(4); // 保存四柱中的四废

        String season = getLunar().getSeason().substring(1, 2); // 获取季节简称（如：春）

        // 1、根据季节判断
        switch (season) {
            case Constant.CHUN_SEASON: // 春
                if (getDayZhu().equals(Constant.GENG_GAN + Constant.SHEN_ZHI) || getDayZhu().equals(Constant.XIN_GAN + Constant.YOU_ZHI)) {
                    list.set(2, Constant.SI_FEI); // 添加日柱神煞
                }
                break;
            case Constant.XIA_SEASON: // 夏
                if (getDayZhu().equals(Constant.REN_GAN + Constant.ZI_ZHI) || getDayZhu().equals(Constant.GUI_GAN + Constant.HAI_ZHI)) {
                    list.set(2, Constant.SI_FEI); // 添加日柱神煞
                }
                break;
            case Constant.QIU_SEASON: // 秋
                if (getDayZhu().equals(Constant.JIA_GAN + Constant.YIN_ZHI) || getDayZhu().equals(Constant.YI_GAN + Constant.MAO_ZHI)) {
                    list.set(2, Constant.SI_FEI); // 添加日柱神煞
                }
                break;
            case Constant.DONG_SEASON: // 冬
                if (getDayZhu().equals(Constant.DING_GAN + Constant.SI_ZHI) || getDayZhu().equals(Constant.BING_GAN + Constant.WU_ZHI)) {
                    list.set(2, Constant.SI_FEI); // 添加日柱神煞
                }
        }

        return list;

    }

    /**
     * ☆计算并返回拱禄
     *
     * @return 四柱神煞：拱禄
     */
    private List<String> gongLu() {

        /*
            【拱禄】算法↓

                1、日柱为'癸亥'，时柱为'癸丑'，拱禄在'子'。
                2、日柱为'癸丑'，时柱为'癸亥'，拱禄在'子'。
                3、日柱为'丁巳'，时柱为'丁未'，拱禄在'午'。
                4、日柱为'戊辰'，时柱为'戊午'，拱禄在'午'。
                5、日柱为'己未'，时柱为'己巳'，拱禄在'巳'。
         */

        List<String> list = CommonUtil.addNullList(4);

        String gongLu = BaZiMap.GONG_LU.get(CommonUtil.addList(getDayZhu(), getHourZhu())); // 根据日柱和时柱获取拱禄位

        // 1、判断年柱
        if (getYearZhi().equals(gongLu)) {
            list.set(0, Constant.GONG_LU);
        }

        // 2、判断月柱
        if (getMonthZhi().equals(gongLu)) {
            list.set(1, Constant.GONG_LU);
        }

        return list;

    }

    /**
     * ☆计算并返回天赦
     *
     * @return 四柱神煞：天赦
     */
    private List<String> tianShe() {

        /*
            【天赦】算法↓

                1、月支是子，日柱为'甲子'，则为天赦；
                2、月支是丑，日柱为'甲子'，则为天赦；
                3、月支是寅，日柱为'戊寅'，则为天赦；
                4、月支是卯，日柱为'戊寅'，则为天赦；
                5、月支是辰，日柱为'戊寅'，则为天赦；
                6、月支是巳，日柱为'甲午'，则为天赦；
                7、月支是午，日柱为'甲午'，则为天赦；
                8、月支是未，日柱为'甲午'，则为天赦；
                9、月支是申，日柱为'戊申'，则为天赦；
                10、月支是酉，日柱为'戊申'，则为天赦；
                11、月支是戌，日柱为'戊申'，则为天赦；
                12、月支是亥，日柱为'甲子'，则为天赦。
         */

        List<String> list = CommonUtil.addNullList(4);

        String _tianSheMonthZhi = BaZiMap.TIAN_SHE.get(getMonthZhi()); // 根据月支获取日柱

        if (getDayZhu().equals(_tianSheMonthZhi)) {
            list.set(2, Constant.TIAN_SHE);
        }

        return list;

    }

    /**
     * ☆计算并返回天转
     *
     * @return 四柱神煞：天转
     */
    private List<String> tianZhuan() {

        /*
            【天转】算法↓

                3、月支是寅、卯、辰，并且日柱时是'乙卯'，则为天转。
                1、月支是巳、午、未，并且日柱时是'丙午'，则为天转。
                2、月支是申、酉、戌，并且日柱时是'辛酉'，则为天转。
                4、月支是亥、子、丑，并且日柱时是'壬子'，则为天转。
         */

        List<String> list = CommonUtil.addNullList(4);

        String _tianZhuanMonthZhu = BaZiMap.TIAN_ZHUAN.get(getMonthZhi()); // 根据月支获取天转落入的四柱

        // 1、判断日柱
        if (getDayZhu().equals(_tianZhuanMonthZhu)) {
            list.set(2, Constant.TIAN_ZHUAN);
        }

        return list;

    }

    /**
     * ☆计算并返回地转
     *
     * @return 四柱神煞：地转
     */
    private List<String> diZhuan() {

        /*
            【地转】算法↓

                3、月支是寅、卯、辰，并且日柱时是'辛卯'，则为地转。
                1、月支是巳、午、未，并且日柱时是'戊午'，则为地转。
                2、月支是申、酉、戌，并且日柱时是'癸酉'，则为地转。
                4、月支是亥、子、丑，并且日柱时是'丙子'，则为地转。
         */

        List<String> list = CommonUtil.addNullList(4);

        String _diZhuanMonthZhU = BaZiMap.DI_ZHUAN.get(getMonthZhi()); // 根据月支判断地转落入的四柱

        // 1、判断日柱
        if (getDayZhu().equals(_diZhuanMonthZhU)) {
            list.set(2, Constant.DI_ZHUAN);
        }

        return list;

    }

    /**
     * ☆计算并返回太极贵人【1】
     *
     * @return 四柱神煞：太极贵人
     */
    private List<String> taiJiGuiRen() {

        /*
            【太极贵人】算法↓

                1、年干或日干为'甲'或者'乙'，并且其他地支有'子'或者'午'的，则为太极贵人；
                2、年干或日干为'丙'或者'丁'，并且其他地支有'酉'或者'卯'的，则为太极贵人；
                3、年干或日干为'庚'或者'辛'，并且其他地支有'寅'或者'亥'的，则为太极贵人；
                4、年干或日干为'壬'或者'癸'，并且其他地支有'巳'或者'申'的，则为太极贵人；
                5、年干或日干为'戊'或者'己'，并且其他地支有'辰'或者'戌'或者'丑'或者'未'的，则为太极贵人。
         */

        List<String> list = CommonUtil.addNullList(4);

        List<String> _taiJiGuiRenYearZhi = BaZiMap.TAI_JI_GUI_REN.get(getYearGan()); // 根据年干获取太极贵人落入的地支
        List<String> _taiJiGuiRenDayZhi = BaZiMap.TAI_JI_GUI_REN.get(getDayGan()); // 根据日干获取太极贵人落入的地支

        // 1、判断年柱
        saveShenSha(list, getYearZhi(), _taiJiGuiRenYearZhi, _taiJiGuiRenDayZhi, 0, Constant.TAI_JI_GUI_REN);
        // 2、判断月柱
        saveShenSha(list, getMonthZhi(), _taiJiGuiRenYearZhi, _taiJiGuiRenDayZhi, 1, Constant.TAI_JI_GUI_REN);
        // 3、判断日柱
        saveShenSha(list, getDayZhi(), _taiJiGuiRenYearZhi, _taiJiGuiRenDayZhi, 2, Constant.TAI_JI_GUI_REN);
        // 4、判断时柱
        saveShenSha(list, getHourZhi(), _taiJiGuiRenYearZhi, _taiJiGuiRenDayZhi, 3, Constant.TAI_JI_GUI_REN);

        return list;

    }

    /**
     * ☆计算并返回天乙贵人【1】
     *
     * @return 四柱神煞：天乙贵人
     */
    private List<String> tianYiGuiRen() {

        /*
            【天乙贵人】算法↓

                1、年干或日干是甲，并且其他地支有'丑'或者'未'的，则为天乙贵人；
                2、年干或日干是乙，并且其他地支有'子'或者'申'的，则为天乙贵人；
                3、年干或日干是丙，并且其他地支有'酉'或者'亥'的，则为天乙贵人；
                4、年干或日干是丁，并且其他地支有'酉'或者'亥'的，则为天乙贵人；
                5、年干或日干是戊，并且其他地支有'丑'或者'未'的，则为天乙贵人；
                6、年干或日干是己，并且其他地支有'子'或者'申'的，则为天乙贵人；
                7、年干或日干是庚，并且其他地支有'丑'或者'未'的，则为天乙贵人；
                8、年干或日干是辛，并且其他地支有'寅'或者'午'的，则为天乙贵人；
                9、年干或日干是壬，并且其他地支有'卯'或者'巳'的，则为天乙贵人；
                10、年干或日干是癸，并且其他地支有'卯'或者'巳'的，则为天乙贵人。
         */

        List<String> list = CommonUtil.addNullList(4);

        List<String> _tianYiGuiRenYearZhi = BaZiMap.TIAN_YI_GUI_REN.get(getYearGan()); // 根据年干获取天乙贵人落入的地支
        List<String> _tianYiGuiRenDayZhi = BaZiMap.TIAN_YI_GUI_REN.get(getDayGan()); // 根据日干获取太极贵人落入的地支

        // 1、判断年柱
        saveShenSha(list, getYearZhi(), _tianYiGuiRenYearZhi, _tianYiGuiRenDayZhi, 0, Constant.TIAN_YI_GUI_REN);
        // 2、判断月柱
        saveShenSha(list, getMonthZhi(), _tianYiGuiRenYearZhi, _tianYiGuiRenDayZhi, 1, Constant.TIAN_YI_GUI_REN);
        // 3、判断日柱
        saveShenSha(list, getDayZhi(), _tianYiGuiRenYearZhi, _tianYiGuiRenDayZhi, 2, Constant.TIAN_YI_GUI_REN);
        // 4、判断时柱
        saveShenSha(list, getHourZhi(), _tianYiGuiRenYearZhi, _tianYiGuiRenDayZhi, 3, Constant.TIAN_YI_GUI_REN);

        return list;

    }

    /**
     * ☆计算并返回福星贵人【1】
     *
     * @return 四柱神煞：福星贵人
     */
    private List<String> fuXingGuiRen() {

        /*
            【福星贵人】算法↓

                1、年干或日干是甲，并且其他地支有'寅'或者'子'的，则为福星贵人；
                2、年干或日干是乙，并且其他地支有'卯'或者'丑'的，则为福星贵人；
                3、年干或日干是丙，并且其他地支有'寅'或者'子'的，则为福星贵人；
                4、年干或日干是丁，并且其他地支有'亥'的，则为福星贵人；
                5、年干或日干是庚，并且其他地支有'午'的，则为福星贵人；
                6、年干或日干是辛，并且其他地支有'巳'的，则为福星贵人；
                7、年干或日干是壬，并且其他地支有'辰'的，则为福星贵人;
                8、年干或日干是癸，并且其他地支有'卯'或者'丑'的，则为福星贵人；
         */

        List<String> list = CommonUtil.addNullList(4);

        List<String> _fuXingGuiRenYearZhi = BaZiMap.FU_XING_GUI_REN.get(getYearGan()); // 根据年干获取福星贵人落入的地支
        List<String> _fuXingGuiRenDayZhi = BaZiMap.FU_XING_GUI_REN.get(getDayGan()); // 根据日干获取福星贵人落入的地支

        // 1、判断年柱
        saveShenSha(list, getYearZhi(), _fuXingGuiRenYearZhi, _fuXingGuiRenDayZhi, 0, Constant.FU_XING_GUI_REN);
        // 2、判断月柱
        saveShenSha(list, getMonthZhi(), _fuXingGuiRenYearZhi, _fuXingGuiRenDayZhi, 1, Constant.FU_XING_GUI_REN);
        // 3、判断日柱
        saveShenSha(list, getDayZhi(), _fuXingGuiRenYearZhi, _fuXingGuiRenDayZhi, 2, Constant.FU_XING_GUI_REN);
        // 4、判断时柱
        saveShenSha(list, getHourZhi(), _fuXingGuiRenYearZhi, _fuXingGuiRenDayZhi, 3, Constant.FU_XING_GUI_REN);

        return list;

    }

    /**
     * ☆计算并返回文昌贵人【2】
     *
     * @return 四柱神煞：文昌贵人
     */
    private List<String> wenChangGuiRen() {

        /*
            【文昌贵人】算法↓

                1、年干或日干是甲，并且其他地支有'巳'的，则为文昌贵人；
                2、年干或日干是乙，并且其他地支有'午'的，则为文昌贵人；
                3、年干或日干是丙，并且其他地支有'申'的，则为文昌贵人；
                4、年干或日干是丁，并且其他地支有'酉'的，则为文昌贵人；
                5、年干或日干是戊，并且其他地支有'申'的，则为文昌贵人；
                6、年干或日干是己，并且其他地支有'酉'的，则为文昌贵人；
                7、年干或日干是庚，并且其他地支有'亥'的，则为文昌贵人；
                8、年干或日干是辛，并且其他地支有'子'的，则为文昌贵人；
                9、年干或日干是壬，并且其他地支有'寅'的，则为文昌贵人；
                10、年干或日干是癸，并且其他地支有'卯'的，则为文昌贵人。
         */

        List<String> list = CommonUtil.addNullList(4);

        String _wenChangGuiRenYearZhi = BaZiMap.WEN_CHANG_GUI_REN.get(getYearGan()); // 根据年干获取文昌贵人落入的地支
        String _wenChangGuiRenDayZhi = BaZiMap.WEN_CHANG_GUI_REN.get(getDayGan()); // 根据日干获取文昌贵人落入的地支

        // 添加神煞
        saveShenSha(list, _wenChangGuiRenYearZhi, _wenChangGuiRenDayZhi, Constant.WEN_CHANG_GUI_REN);

        return list;

    }

    /**
     * ☆计算并返回天厨贵人【2】
     *
     * @return 四柱神煞：天厨贵人
     */
    private List<String> tianChuGuiRen() {

        /*
            【天厨贵人】算法↓

                1、年干或日干是甲，并且其他地支有'巳'的，则为天厨贵人；
                2、年干或日干是乙，并且其他地支有'午'的，则为天厨贵人；
                3、年干或日干是丙，并且其他地支有'巳'的，则为天厨贵人；
                4、年干或日干是丁，并且其他地支有'午'的，则为天厨贵人；
                5、年干或日干是戊，并且其他地支有'申'的，则为天厨贵人；
                6、年干或日干是己，并且其他地支有'酉'的，则为天厨贵人；
                7、年干或日干是庚，并且其他地支有'亥'的，则为天厨贵人；
                8、年干或日干是辛，并且其他地支有'子'的，则为天厨贵人；
                9、年干或日干是壬，并且其他地支有'寅'的，则为天厨贵人；
                10、年干或日干是癸，并且其他地支有'卯'的，则为天厨贵人。
         */

        List<String> list = CommonUtil.addNullList(4);

        String _tianChuGuiRenYearZhi = BaZiMap.TIAN_CHU_GUI_REN.get(getYearGan()); // 根据年干获取天厨贵人落入的地支
        String _tianChuGuiRenDayZhi = BaZiMap.TIAN_CHU_GUI_REN.get(getDayGan()); // 根据日干获取天厨贵人落入的地支

        // 添加神煞
        saveShenSha(list, _tianChuGuiRenYearZhi, _tianChuGuiRenDayZhi, Constant.TIAN_CHU_GUI_REN);

        return list;

    }

    /**
     * ☆计算并返回国印【2】
     *
     * @return 四柱神煞：国印
     */
    private List<String> guoYin() {

        /*
            【国印】算法↓

                1、年干或日干为甲，并且其他地支有'戌'的，则为国印。
                2、年干或日干为乙，并且其他地支有'亥'的，则为国印。
                3、年干或日干为丙，并且其他地支有'丑'的，则为国印。
                4、年干或日干为丁，并且其他地支有'寅'的，则为国印。
                5、年干或日干为戊，并且其他地支有'丑'的，则为国印。
                6、年干或日干为己，并且其他地支有'寅'的，则为国印。
                7、年干或日干为庚，并且其他地支有'辰'的，则为国印。
                8、年干或日干为辛，并且其他地支有'巳'的，则为国印。
                9、年干或日干为壬，并且其他地支有'未'的，则为国印。
                10、年干或日干为癸，并且其他地支有'申'的，则为国印。
         */

        List<String> list = CommonUtil.addNullList(4);

        String _guoYinYearZhi = BaZiMap.GUO_YIN.get(getYearGan()); // 根据年干获取国印落入的地支
        String _guoYinDayZhi = BaZiMap.GUO_YIN.get(getDayGan()); // 根据日干获取国印落入的地支

        // 添加神煞
        saveShenSha(list, _guoYinYearZhi, _guoYinDayZhi, Constant.GUO_YIN);

        return list;

    }

    /**
     * ☆计算并返回驿马【2】
     *
     * @return 四柱神煞：驿马
     */
    private List<String> yiMa() {

        /*
            【驿马】算法↓

                1、年支或日支是申、子、辰，并且其他地支有'寅'的，则为驿马。
                2、年支或日支是寅、午、戌，并且其他地支有'申'的，则为驿马。
                3、年支或日支是亥、卯、未，并且其他地支有'巳'的，则为驿马。
                4、年支或日支是巳、酉、丑，并且其他地支有'亥'的，则为驿马。
         */

        List<String> list = CommonUtil.addNullList(4);

        String _yiMaYearZhi = BaZiMap.YI_MA.get(getYearZhi()); // 根据年支获取驿马落入的地支
        String _yiMaDayZhi = BaZiMap.YI_MA.get(getDayZhi()); // 根据日支获取驿马落入的地支

        // 添加神煞
        saveShenSha(list, _yiMaYearZhi, _yiMaDayZhi, Constant.YI_MA);

        return list;

    }

    /**
     * ☆计算并返回华盖【2】
     *
     * @return 四柱神煞：华盖
     */
    private List<String> huaGai() {

        /*
            【华盖】算法↓

                1、年支或日支是申、子、辰，并且其他地支有'辰'的，则为华盖。
                2、年支或日支是寅、午、戌，并且其他地支有'戌'的，则为华盖。
                3、年支或日支是巳、酉、丑，并且其他地支有'丑'的，则为华盖。
                4、年支或日支是亥、卯、未，并且其他地支有'未'的，则为华盖。
         */

        List<String> list = CommonUtil.addNullList(4);

        String _huaGaiYearZhi = BaZiMap.HUA_GAI.get(getYearZhi()); // 根据年支获取华盖落入的地支
        String _huaGaiDayZhi = BaZiMap.HUA_GAI.get(getDayZhi()); // 根据日支判获取盖落入的地支

        // 添加神煞
        saveShenSha(list, _huaGaiYearZhi, _huaGaiDayZhi, Constant.HUA_GAI);

        return list;

    }

    /**
     * ☆计算并返回劫煞【2】
     *
     * @return 四柱神煞：劫煞
     */
    private List<String> jieSha() {

        /*
            【劫煞】算法↓

                1、年支或日支是巳、酉、丑，并且其他地支有'寅'的，则为劫煞。
                2、年支或日支是亥、卯、未，并且其他地支有'申'的，则为劫煞。
                3、年支或日支是申、子、辰，并且其他地支有'巳'的，则为劫煞。
                4、年支或日支是寅、午、戌，并且其他地支有'亥'的，则为劫煞。
         */

        List<String> list = CommonUtil.addNullList(4);

        String _jieShaYearZhi = BaZiMap.JIE_SHA.get(getYearZhi()); // 根据年支获取劫煞落入的地支
        String _jieShaDayZhi = BaZiMap.JIE_SHA.get(getDayZhi()); // 根据日支获取劫煞落入的地支

        // 添加神煞
        saveShenSha(list, _jieShaYearZhi, _jieShaDayZhi, Constant.JIE_SHA);

        return list;


    }

    /**
     * ☆计算并返回将星【2】
     *
     * @return 四柱神煞：将星
     */
    private List<String> jiangXing() {

        /*
            【将星】算法↓

                1、年支或日支是申、子、辰，并且其他地支有'子'的，则为将星。
                2、年支或日支是寅、午、戌，并且其他地支有'午'的，则为将星。
                3、年支或日支是亥、卯、未，并且其他地支有'卯'的，则为将星。
                4、年支或日支是巳、酉、丑，并且其他地支有'酉'的，则为将星。
         */

        List<String> list = CommonUtil.addNullList(4);

        String _jiangXingYearZhi = BaZiMap.JIANG_XING.get(getYearZhi()); // 根据年支获取将星落入的地支
        String _jiangXingDayZhi = BaZiMap.JIANG_XING.get(getDayZhi()); // 根据日支获取将星落入的地支

        // 添加神煞
        saveShenSha(list, _jiangXingYearZhi, _jiangXingDayZhi, Constant.JIANG_XING);

        return list;

    }

    /**
     * ☆计算并返回桃花【2】
     *
     * @return 四柱神煞：桃花
     */
    private List<String> taoHua() {

        /*
            【桃花】算法↓

                1、年支或日支是亥、卯、未，并且其他地支有'子'的，则为桃花。
                2、年支或日支是巳、酉、丑，并且其他地支有'午'的，则为桃花。
                3、年支或日支是寅、午、戌，并且其他地支有'卯'的，则为桃花。
                4、年支或日支是申、子、辰，并且其他地支有'酉'的，则为桃花。
         */

        List<String> list = CommonUtil.addNullList(4);

        String _taoHuaYearZhi = BaZiMap.TAO_HUA.get(getYearZhi()); // 根据年支获取桃花落入的地支
        String _taoHuaDayZhi = BaZiMap.TAO_HUA.get(getDayZhi()); // 根据日支获取桃花落入的地支

        // 添加神煞
        saveShenSha(list, _taoHuaYearZhi, _taoHuaDayZhi, Constant.TAO_HUA);

        return list;

    }

    /**
     * ☆计算并返回亡神【2】
     *
     * @return 四柱神煞：亡神
     */
    private List<String> wangShen() {

        /*
            【亡神】算法↓

                1、年支或日支是亥、卯、未，并且其他地支有'寅'的，则为亡神。
                2、年支或日支是巳、酉、丑，并且其他地支有'申'的，则为亡神。
                3、年支或日支是寅、午、戌，并且其他地支有'巳'的，则为亡神。
                4、年支或日支是申、子、辰，并且其他地支有'亥'的，则为亡神。
         */

        List<String> list = CommonUtil.addNullList(4);

        String _wangShenYearZhi = BaZiMap.WANG_SHEN.get(getYearZhi()); // 根据年支获取亡神落入的地支
        String _wangShenDayZhi = BaZiMap.WANG_SHEN.get(getDayZhi()); // 根据日支获取亡神落入的地支

        // 添加神煞
        saveShenSha(list, _wangShenYearZhi, _wangShenDayZhi, Constant.WANG_SHEN);

        return list;

    }

    /**
     * ☆计算并返回丧门【2】
     *
     * @return 四柱神煞：丧门
     */
    private List<String> sangMen() {

        /*
            【丧门】算法↓

                1、年支或日支是子，并且其他地支有'寅'的，则为丧门；
                2、年支或日支是丑，并且其他地支有'卯'的，则为丧门；
                3、年支或日支是寅，并且其他地支有'辰'的，则为丧门；
                4、年支或日支是卯，并且其他地支有'巳'的，则为丧门；
                5、年支或日支是辰，并且其他地支有'午'的，则为丧门；
                6、年支或日支是巳，并且其他地支有'未'的，则为丧门；
                7、年支或日支是午，并且其他地支有'申'的，则为丧门；
                8、年支或日支是未，并且其他地支有'酉'的，则为丧门；
                9、年支或日支是申，并且其他地支有'戌'的，则为丧门；
                10、年支或日支是酉，并且其他地支有'亥'的，则为丧门；
                11、年支或日支是戌，并且其他地支有'子'的，则为丧门；
                12、年支或日支是亥，并且其他地支有'丑'的，则为丧门。
         */

        List<String> list = CommonUtil.addNullList(4);

        String _sangMenYearZhi = BaZiMap.SANG_MEN.get(getYearZhi()); // 根据年支获取丧门落入的地支
        String _sangMenDayMZhi = BaZiMap.SANG_MEN.get(getDayZhi()); // 根据月支获取丧门落入的地支

        // 添加神煞
        saveShenSha(list, _sangMenYearZhi, _sangMenDayMZhi, Constant.SANG_MEN);

        return list;

    }

    /**
     * ☆计算并返回吊客【2】
     *
     * @return 四柱神煞：吊客
     */
    private List<String> diaoKe() {

        /*
            【吊客】算法↓

                1、年支或日支是子，并且其他地支有'戌'的，则为吊客；
                2、年支或日支是丑，并且其他地支有'亥'的，则为吊客；
                3、年支或日支是寅，并且其他地支有'子'的，则为吊客；
                4、年支或日支是卯，并且其他地支有'丑'的，则为吊客；
                5、年支或日支是辰，并且其他地支有'寅'的，则为吊客；
                6、年支或日支是巳，并且其他地支有'卯'的，则为吊客；
                7、年支或日支是午，并且其他地支有'辰'的，则为吊客；
                8、年支或日支是未，并且其他地支有'巳'的，则为吊客；
                9、年支或日支是申，并且其他地支有'午'的，则为吊客；
                10、年支或日支是酉，并且其他地支有'未'的，则为吊客；
                11、年支或日支是戌，并且其他地支有'申'的，则为吊客；
                12、年支或日支是亥，并且其他地支有'酉'的，则为吊客。
         */

        List<String> list = CommonUtil.addNullList(4);

        String _diaoKeYearZhi = BaZiMap.DIAO_KE.get(getYearZhi()); // 根据年支获取吊客落入的地支
        String _diaoKeDayMZhi = BaZiMap.DIAO_KE.get(getDayZhi()); // 根据月支获取吊客落入的地支

        // 添加神煞
        saveShenSha(list, _diaoKeYearZhi, _diaoKeDayMZhi, Constant.DIAO_KE);

        return list;

    }

    /**
     * ☆计算并返回披麻【2】
     *
     * @return 四柱神煞：披麻
     */
    private List<String> piMa() {

        /*
            【披麻】算法↓

                1、年支或日支是子，并且其他地支有'酉'的，则为披麻；
                2、年支或日支是丑，并且其他地支有'戌'的，则为披麻；
                3、年支或日支是寅，并且其他地支有'亥'的，则为披麻；
                4、年支或日支是卯，并且其他地支有'子'的，则为披麻；
                5、年支或日支是辰，并且其他地支有'丑'的，则为披麻；
                6、年支或日支是巳，并且其他地支有'寅'的，则为披麻；
                7、年支或日支是午，并且其他地支有'卯'的，则为披麻；
                8、年支或日支是未，并且其他地支有'辰'的，则为披麻；
                9、年支或日支是申，并且其他地支有'巳'的，则为披麻；
                10、年支或日支是酉，并且其他地支有'午'的，则为披麻；
                11、年支或日支是戌，并且其他地支有'未'的，则为披麻；
                12、年支或日支是亥，并且其他地支有'申'的，则为披麻。
         */

        List<String> list = CommonUtil.addNullList(4);

        String _piMaYearZhi = BaZiMap.PI_MA.get(getYearZhi()); // 根据年支获取披麻落入的地支
        String _piMaDayMZhi = BaZiMap.PI_MA.get(getDayZhi()); // 根据月支获取披麻落入的地支

        // 添加神煞
        saveShenSha(list, _piMaYearZhi, _piMaDayMZhi, Constant.PI_MA);

        return list;

    }

    /**
     * ☆计算并返回阴差阳错【3】
     *
     * @return 四柱神煞：阴差阳错
     */
    private List<String> yinChaYangCuo() {

        /*
            【阴差阳错】算法↓

                日柱：丙午 丙子 丁未 丁丑 戊申 戊寅 辛酉 辛卯 壬戌 壬辰 癸巳 癸亥
         */

        List<String> list = CommonUtil.addNullList(4);

        // 添加神煞
        saveShenSha(list, getDayZhu(), BaZiMap.YIN_CHA_YANG_CUO, Constant.YIN_CHA_YANG_CUO);

        return list;

    }

    /**
     * ☆计算并返回十恶大败【3】
     *
     * @return 四柱神煞：十恶大败
     */
    private List<String> shiEDaBai() {

        /*
            【十恶大败】算法↓

                日柱：甲辰 乙巳 丙申 丁亥 戊戌 己丑 庚辰 辛巳 壬申 癸亥
         */

        List<String> list = CommonUtil.addNullList(4);

        // 添加神煞
        saveShenSha(list, getDayZhu(), BaZiMap.SHI_E_DA_BAI, Constant.SHI_E_DA_BAI);

        return list;

    }

    /**
     * ☆计算并返回孤鸾煞【3】
     *
     * @return 四柱神煞：孤鸾煞
     */
    private List<String> guLuanSha() {

        /*
            【孤鸾煞】算法↓

                日柱：乙巳、丁巳、辛亥、戊申、甲寅、丙午、戊午、壬子
         */

        List<String> list = CommonUtil.addNullList(4);

        // 添加神煞
        saveShenSha(list, getDayZhu(), BaZiMap.GU_LUAN_SHA, Constant.GU_LUAN_SHA);

        return list;

    }

    /**
     * ☆计算并返回魁罡【3】
     *
     * @return 四柱神煞：魁罡
     */
    private List<String> kuiGang() {

        /*
            【魁罡】算法↓

                日柱：壬辰，庚戍，庚辰，戊戍
         */

        List<String> list = CommonUtil.addNullList(4);

        // 添加神煞
        saveShenSha(list, getDayZhu(), BaZiMap.KUI_GANG, Constant.KUI_GANG);

        return list;

    }

    /**
     * ☆计算并返回八专【3】
     *
     * @return 四柱神煞：八专
     */
    private List<String> baZhuan() {

        /*
            【八专】算法↓

                日柱：甲寅 乙卯 丁未 戊戌 己未 庚申 辛酉 癸丑
         */

        List<String> list = CommonUtil.addNullList(4);

        // 添加神煞
        saveShenSha(list, getDayZhu(), BaZiMap.BA_ZHUAN, Constant.BA_ZHUAN);

        return list;

    }

    /**
     * ☆计算并返回九丑【3】
     *
     * @return 四柱神煞：九丑
     */
    private List<String> jiuChou() {

        /*
            【九丑】算法↓

                日柱：戊子 丁酉 丁卯 戊午 己酉 己卯 壬子 壬午 辛卯
         */

        List<String> list = CommonUtil.addNullList(4);

        // 添加神煞
        saveShenSha(list, getDayZhu(), BaZiMap.JIU_CHOU, Constant.JIU_CHOU);

        return list;

    }

    /**
     * ☆计算并返回十灵【3】
     *
     * @return 四柱神煞：十灵
     */
    private List<String> shiLing() {

        /*
            【十灵】算法↓

                日柱：甲辰、乙亥、丙辰、丁酉、戊午、庚戌、庚寅、辛亥、壬寅、癸未
         */

        List<String> list = CommonUtil.addNullList(4);

        // 添加神煞
        saveShenSha(list, getDayZhu(), BaZiMap.SHI_LING, Constant.SHI_LING_RI);

        return list;

    }

    /**
     * ☆计算并返回六秀【3】
     *
     * @return 四柱神煞：六秀
     */
    private List<String> liuXiu() {

        /*
            【六秀】算法↓

                日柱：丙午 丁未 戊子 戊午 己丑 己未
         */

        List<String> list = CommonUtil.addNullList(4);

        // 添加神煞
        saveShenSha(list, getDayZhu(), BaZiMap.LIU_XIU, Constant.LIU_XIU_RI);

        return list;

    }

    /**
     * ☆计算并返回学堂【4】
     *
     * @param search 1:禄命法，2:子平法（默认查法：禄命法）
     * @return 四柱神煞：学堂
     */
    private List<String> xueTang(int search) {

        /*
            【学堂】算法↓

                一、禄命法：（以年柱纳音查月支、日支、时支）
                    1、年命属木，月支或日支或时支有'亥'的，则为学堂。（'己亥'为正学堂）
                    2、年命属火，月支或日支或时支有'寅'的，则为学堂。（'丙寅'为正学堂）
                    3、年命属土，月支或日支或时支有'申'的，则为学堂。（'戊申'为正学堂）
                    4、年命属金，月支或日支或时支有'巳'的，则为学堂。（'辛巳'为正学堂）
                    5、年命属水，月支或日支或时支有'申'的，则为学堂。（'甲申'为正学堂）


                二、子平法：（以年干、日干查四柱）
                    1、年干或日干为甲，并且其他天干地支有'已'或者'亥'的，则为学堂。
                    2、年干或日干为乙，并且其他天干地支有'壬'或者'午'的，则为学堂。
                    3、年干或日干为丙，并且其他天干地支有'丙'或者'寅'的，则为学堂。
                    4、年干或日干为丁，并且其他天干地支有'丁'或者'酉'的，则为学堂。
                    5、年干或日干为戊，并且其他天干地支有'戊'或者'寅'的，则为学堂。
                    6、年干或日干为己，并且其他天干地支有'己'或者'酉'的，则为学堂。
                    7、年干或日干为庚，并且其他天干地支有'辛'或者'巳'的，则为学堂。
                    8、年干或日干为辛，并且其他天干地支有'甲'或者'子'的，则为学堂。
                    9、年干或日干为壬，并且其他天干地支有'甲'或者'申'的，则为学堂。
                    10、年干或日干为癸，并且其他天干地支有'乙'或者'卯'的，则为学堂。
         */

        // 数据校验
        if (search < 1) search = 1;
        if (search > 1) search = 2;

        List<String> list = CommonUtil.addNullList(4);

        // 1、禄命法
        if (search == 1) {
            String yearMingWuXing = getYearZhuNaYin().substring(2, 3); // 年命五行
            // 1.1、年命属木，月支或日支或时支有'亥'的，则为学堂。（'己亥'为正学堂）
            saveShenSha(list, yearMingWuXing, Constant.MU, Constant.HAI_ZHI, Constant.XUE_TANG);
            // 1.2、年命属火，月支或日支或时支有'寅'的，则为学堂。（'丙寅'为正学堂）
            saveShenSha(list, yearMingWuXing, Constant.HUO, Constant.YIN_ZHI, Constant.XUE_TANG);
            // 1.3、年命属土，月支或日支或时支有'申'的，则为学堂。（'戊申'为正学堂）
            saveShenSha(list, yearMingWuXing, Constant.TU, Constant.SHEN_ZHI, Constant.XUE_TANG);
            // 1.4、年命属金，月支或日支或时支有'巳'的，则为学堂。（'辛巳'为正学堂）
            saveShenSha(list, yearMingWuXing, Constant.JIN, Constant.SI_ZHI, Constant.XUE_TANG);
            // 1.5、年命属水，月支或日支或时支有'申'的，则为学堂。（'甲申'为正学堂）
            saveShenSha(list, yearMingWuXing, Constant.SHUI, Constant.SHEN_ZHI, Constant.XUE_TANG);
        }

        // 2、子平法
        if (search == 2) {
            List<String> _xueTangYearGanZhi = BaZiMap.XUE_TANG.get(getYearGan()); // 根据年干获取学堂落入的天干或地支
            List<String> _xueTangDayGanZhi = BaZiMap.XUE_TANG.get(getDayGan()); // 根据日干获取学堂落入的天干或地支
            // 2.1、根据年干判断
            saveShenSha(list, _xueTangYearGanZhi, Constant.XUE_TANG);
            // 2.2、根据日干判断
            saveShenSha(list, _xueTangDayGanZhi, Constant.XUE_TANG);
        }

        return list;

    }

    /**
     * ☆计算并返回词馆【4】
     *
     * @param search 1:禄命法，2:子平法（默认查法：禄命法）
     * @return 四柱神煞：词馆
     */
    private List<String> ciGuan(int search) {

        /*
            【词馆】算法↓

                一、禄命法：（以年柱纳音查月支、日支、时支）
                    1、年命属木，月支或日支或时支有'寅'的，则为词馆。（'庚寅'为正词馆）
                    2、年命属火，月支或日支或时支有'巳'的，则为词馆。（'乙巳'为正词馆）
                    3、年命属土，月支或日支或时支有'亥'的，则为词馆。（'丁亥'为正词馆）
                    4、年命属金，月支或日支或时支有'申'的，则为词馆。（'壬申'为正词馆）
                    5、年命属水，月支或日支或时支有'亥'的，则为词馆。（'癸亥'为正词馆）


                二、子平法：（以年干、日干查四柱）
                    1、年干或日干为甲，并且其他天干地支有'已'或者'亥'的，则为词馆。
                    2、年干或日干为乙，并且其他天干地支有'壬'或者'午'的，则为词馆。
                    3、年干或日干为丙，并且其他天干地支有'丙'或者'寅'的，则为词馆。
                    4、年干或日干为丁，并且其他天干地支有'丁'或者'酉'的，则为词馆。
                    5、年干或日干为戊，并且其他天干地支有'戊'或者'寅'的，则为词馆。
                    6、年干或日干为己，并且其他天干地支有'己'或者'酉'的，则为词馆。
                    7、年干或日干为庚，并且其他天干地支有'辛'或者'巳'的，则为词馆。
                    8、年干或日干为辛，并且其他天干地支有'甲'或者'子'的，则为词馆。
                    9、年干或日干为壬，并且其他天干地支有'甲'或者'申'的，则为词馆。
                    10、年干或日干为癸，并且其他天干地支有'乙'或者'卯'的，则为词馆。
         */

        // 数据校验
        if (search < 1) search = 1;
        if (search > 1) search = 2;

        List<String> list = CommonUtil.addNullList(4);

        // 1、禄命法
        if (search == 1) {
            String yearMingWuXing = getYearZhuNaYin().substring(2, 3); // 年命五行
            // 1.1、年命属木，月支或日支或时支有'寅'的，则为词馆。（'庚寅'为正词馆）
            saveShenSha(list, yearMingWuXing, Constant.MU, Constant.HAI_ZHI, Constant.CI_GUAN);
            // 1.2、年命属火，月支或日支或时支有'巳'的，则为词馆。（'乙巳'为正词馆）
            saveShenSha(list, yearMingWuXing, Constant.HUO, Constant.YIN_ZHI, Constant.CI_GUAN);
            // 1.3、年命属土，月支或日支或时支有'亥'的，则为词馆。（'丁亥'为正词馆）
            saveShenSha(list, yearMingWuXing, Constant.TU, Constant.SHEN_ZHI, Constant.CI_GUAN);
            // 1.4、年命属金，月支或日支或时支有'申'的，则为词馆。（'壬申'为正词馆）
            saveShenSha(list, yearMingWuXing, Constant.JIN, Constant.SI_ZHI, Constant.CI_GUAN);
            // 1.5、年命属水，月支或日支或时支有'亥'的，则为词馆。（'癸亥'为正词馆）
            saveShenSha(list, yearMingWuXing, Constant.SHUI, Constant.SHEN_ZHI, Constant.CI_GUAN);
        }

        // 2、子平法
        if (search == 2) {
            List<String> _ciGuanYearGanZhi = BaZiMap.CI_GUAN.get(getYearGan()); // 根据年干获取词馆落入的天干或地支
            List<String> _ciGuanDayGanZhi = BaZiMap.CI_GUAN.get(getDayGan()); // 根据日干获取词馆落入的天干或地支
            // 2.1、根据年干判断
            saveShenSha(list, _ciGuanYearGanZhi, Constant.CI_GUAN);
            // 2.2、根据日干判断
            saveShenSha(list, _ciGuanDayGanZhi, Constant.CI_GUAN);
        }

        return list;

    }

    /**
     * ☆计算并返回红艳煞【5】
     *
     * @return 四柱神煞：红艳煞
     */
    private List<String> hongYanSha() {

        /*
            【红艳煞】算法↓

                1、日干为甲，并且其他地支有'午'的，为红艳煞。
                2、日干为乙，并且其他地支有'申'的，为红艳煞。
                3、日干为丙，并且其他地支有'寅'的，为红艳煞。
                4、日干为丁，并且其他地支有'未'的，为红艳煞。
                5、日干为戊，并且其他地支有'辰'的，为红艳煞。
                6、日干为己，并且其他地支有'辰'的，为红艳煞。
                7、日干为庚，并且其他地支有'戌'的，为红艳煞。
                8、日干为辛，并且其他地支有'酉'的，为红艳煞。
                9、日干为壬，并且其他地支有'子'的，为红艳煞。
                10、日干为癸，并且其他地支有'申'的，为红艳煞。
         */

        List<String> list = CommonUtil.addNullList(4);

        String _hongYanShaDayZhi = BaZiMap.HONG_YAN_SHA.get(getDayGan()); // 根据日干获取红艳煞落入的地支

        saveShenSha(list, _hongYanShaDayZhi, Constant.JIN_YU);

        return list;

    }

    /**
     * ☆计算并返回金舆【5】
     *
     * @return 四柱神煞：金舆
     */
    private List<String> jinYu() {

        /*
            【金舆】算法↓

                1、年干或日干为甲，并且其他地支有'辰'的，则为金舆。
                2、年干或日干为乙，并且其他地支有'巳'的，则为金舆。
                3、年干或日干为丙，并且其他地支有'未'的，则为金舆。
                4、年干或日干为丁，并且其他地支有'申'的，则为金舆。
                5、年干或日干为戊，并且其他地支有'未'的，则为金舆。
                6、年干或日干为己，并且其他地支有'申'的，则为金舆。
                7、年干或日干为庚，并且其他地支有'戌'的，则为金舆。
                8、年干或日干为辛，并且其他地支有'亥'的，则为金舆。
                9、年干或日干为壬，并且其他地支有'丑'的，则为金舆。
                10、年干或日干为癸，并且其他地支有'寅'的，则为金舆。
         */

        List<String> list = CommonUtil.addNullList(4);

        String _jinYuYearZhi = BaZiMap.JIN_YU.get(getYearGan()); // 根据年干获取金舆落入的地支
        String _jinYuDayZhi = BaZiMap.JIN_YU.get(getDayGan()); // 根据日干获取金舆落入的地支

        // 1、判断年柱
        saveShenSha(list, _jinYuYearZhi, Constant.JIN_YU);
        // 2、判断日柱
        saveShenSha(list, _jinYuDayZhi, Constant.JIN_YU);

        return list;

    }

    /**
     * ☆计算并返回羊刃【5】
     *
     * @return 四柱神煞：羊刃
     */
    private List<String> yangRen() {

        /*
            【羊刃】算法↓

                1、日干为甲，并且其他地支有'卯'的，则为羊刃。
                2、日干为乙，并且其他地支有'辰'的，则为羊刃。
                3、日干为丙，并且其他地支有'午'的，则为羊刃。
                4、日干为丁，并且其他地支有'未'的，则为羊刃。
                5、日干为戊，并且其他地支有'午'的，则为羊刃。
                6、日干为己，并且其他地支有'未'的，则为羊刃。
                7、日干为庚，并且其他地支有'酉'的，则为羊刃。
                8、日干为辛，并且其他地支有'戌'的，则为羊刃。
                9、日干为壬，并且其他地支有'子'的，则为羊刃。
                10、日干为癸，并且其他地支有'丑'的，则为羊刃。
         */

        List<String> list = CommonUtil.addNullList(4);

        String _yangRenDayZhi = BaZiMap.YANG_REN.get(getDayGan()); // 根据日干获取羊刃落入的地支

        // 添加神煞
        saveShenSha(list, _yangRenDayZhi, Constant.YANG_REN);

        return list;

    }

    /**
     * ☆计算并返回飞刃【5】
     *
     * @return 四柱神煞：飞刃
     */
    private List<String> feiRen() {

        /*
            【飞刃】算法↓

                1、日干为甲，并且其他地支有'酉'的，则为飞刃。
                2、日干为乙，并且其他地支有'寅'的，则为飞刃。
                3、日干为丙，并且其他地支有'子'的，则为飞刃。
                4、日干为丁，并且其他地支有'亥'的，则为飞刃。
                5、日干为戊，并且其他地支有''的，则为飞刃。
                6、日干为己，并且其他地支有''的，则为飞刃。
                7、日干为庚，并且其他地支有'卯'的，则为飞刃。
                8、日干为辛，并且其他地支有'寅'的，则为飞刃。
                9、日干为壬，并且其他地支有'午'的，则为飞刃。
                10、日干为癸，并且其他地支有'巳'的，则为飞刃。
         */

        List<String> list = CommonUtil.addNullList(4);

        String _feiRenDayZhi = BaZiMap.FEI_REN.get(getDayGan()); // 根据日干获取飞刃落入的地支

        // 添加神煞
        saveShenSha(list, _feiRenDayZhi, Constant.FEI_REN);

        return list;

    }

    /**
     * ☆计算并返回血刃【5】
     *
     * @return 四柱神煞：血刃
     */
    private List<String> xueRen() {

        /*
            【血刃】算法↓

                1、月支为子，并且其他地支有'午'的，则为血刃。
                2、月支为丑，并且其他地支有'子'的，则为血刃。
                3、月支为寅，并且其他地支有'丑'的，则为血刃。
                4、月支为卯，并且其他地支有'未'的，则为血刃。
                5、月支为辰，并且其他地支有'寅'的，则为血刃。
                6、月支为巳，并且其他地支有'申'的，则为血刃。
                7、月支为午，并且其他地支有'卯'的，则为血刃。
                8、月支为未，并且其他地支有'酉'的，则为血刃。
                9、月支为申，并且其他地支有'辰'的，则为血刃。
                10、月支为酉，并且其他地支有'戌'的，则为血刃。
                11、月支为戌，并且其他地支有'巳'的，则为血刃。
                12、月支为亥，并且其他地支有'亥'的，则为血刃。
         */

        List<String> list = CommonUtil.addNullList(4);

        String _yangRenMonthZhi = BaZiMap.XUE_REN.get(getMonthZhi()); // 根据月支获取血刃落入的地支

        // 添加神煞
        saveShenSha(list, _yangRenMonthZhi, Constant.XUE_REN);

        return list;

    }

    /**
     * ☆计算并返回流霞【5】
     *
     * @return 四柱神煞：流霞
     */
    private List<String> liuXia() {

        /*
            【流霞】算法↓

                1、日干为甲，并且其他地支有'酉'的，则为流霞。
                2、日干为乙，并且其他地支有'戌'的，则为流霞。
                3、日干为丙，并且其他地支有'未'的，则为流霞。
                4、日干为丁，并且其他地支有'申'的，则为流霞。
                5、日干为戊，并且其他地支有'巳'的，则为流霞。
                6、日干为己，并且其他地支有'午'的，则为流霞。
                7、日干为庚，并且其他地支有'辰'的，则为流霞。
                8、日干为辛，并且其他地支有'卯'的，则为流霞。
                9、日干为壬，并且其他地支有'亥'的，则为流霞。
                10、日干为癸，并且其他地支有'寅'的，则为流霞。
         */

        List<String> list = CommonUtil.addNullList(4);

        String _yangRenDayZhi = BaZiMap.LIU_XIA.get(getDayGan()); // 根据日干获取流霞落入的地支

        // 添加神煞
        saveShenSha(list, _yangRenDayZhi, Constant.LIU_XIA);

        return list;

    }

    /**
     * ☆计算并返回天医【5】
     *
     * @return 四柱神煞：天医
     */
    private List<String> tianYi() {

        /*
            【天医】算法↓

                1、月支为子，并且其他地支有'亥'的，则为天医。
                2、月支为丑，并且其他地支有'子'的，则为天医。
                3、月支为寅，并且其他地支有'丑'的，则为天医。
                4、月支为卯，并且其他地支有'寅'的，则为天医。
                5、月支为辰，并且其他地支有'卯'的，则为天医。
                6、月支为巳，并且其他地支有'辰'的，则为天医。
                7、月支为午，并且其他地支有'巳'的，则为天医。
                8、月支为未，并且其他地支有'午'的，则为天医。
                9、月支为申，并且其他地支有'未'的，则为天医。
                10、月支为酉，并且其他地支有'申'的，则为天医。
                11、月支为戌，并且其他地支有'酉'的，则为天医。
                12、月支为亥，并且其他地支有'戌'的，则为天医。
         */

        List<String> list = CommonUtil.addNullList(4);

        String _tianYiZhi = BaZiMap.TIAN_YI.get(getMonthZhi()); // 根据月支获取天医落入的地支

        // 添加神煞
        saveShenSha(list, _tianYiZhi, Constant.TIAN_YI);

        return list;

    }

    /**
     * ☆计算并返回天喜【5】
     *
     * @return 四柱神煞：天喜
     */
    private List<String> tianXi() {

        /*
            【天喜】算法↓

                1、年支为子，并且其他地支有'酉'的，则为天喜。
                2、年支为丑，并且其他地支有'申'的，则为天喜。
                3、年支为寅，并且其他地支有'未'的，则为天喜。
                4、年支为卯，并且其他地支有'午'的，则为天喜。
                5、年支为辰，并且其他地支有'巳'的，则为天喜。
                6、年支为巳，并且其他地支有'辰'的，则为天喜。
                7、年支为午，并且其他地支有'卯'的，则为天喜。
                8、年支为未，并且其他地支有'寅'的，则为天喜。
                9、年支为申，并且其他地支有'丑'的，则为天喜。
                10、年支为酉，并且其他地支有'子'的，则为天喜。
                11、年支为戌，并且其他地支有'亥'的，则为天喜。
                12、年支为亥，并且其他地支有'戌'的，则为天喜。
         */

        List<String> list = CommonUtil.addNullList(4);

        String _tianXiYearZhi = BaZiMap.TIAN_XI.get(getYearZhi()); // 根据年支获取天喜落入的地支

        // 添加神煞
        saveShenSha(list, _tianXiYearZhi, Constant.TIAN_XI);

        return list;

    }

    /**
     * ☆计算并返回红鸾【5】
     *
     * @return 四柱神煞：红鸾
     */
    private List<String> hongLuan() {

        /*
            【红鸾】算法↓

                1、年支为子，并且其他地支有'卯'的，则为红鸾。
                2、年支为丑，并且其他地支有'寅'的，则为红鸾。
                3、年支为寅，并且其他地支有'丑'的，则为红鸾。
                4、年支为卯，并且其他地支有'子'的，则为红鸾。
                5、年支为辰，并且其他地支有'亥'的，则为红鸾。
                6、年支为巳，并且其他地支有'戌'的，则为红鸾。
                7、年支为午，并且其他地支有'酉'的，则为红鸾。
                8、年支为未，并且其他地支有'申'的，则为红鸾。
                9、年支为申，并且其他地支有'未'的，则为红鸾。
                10、年支为酉，并且其他地支有'午'的，则为红鸾。
                11、年支为戌，并且其他地支有'巳'的，则为红鸾。
                12、年支为亥，并且其他地支有'辰'的，则为红鸾。
         */

        List<String> list = CommonUtil.addNullList(4);

        String _hongLuanZhi = BaZiMap.HONG_LUAN.get(getYearZhi()); // 根据年支获取红鸾落入的地支

        // 添加神煞
        saveShenSha(list, _hongLuanZhi, Constant.HONG_LUAN);

        return list;

    }

    /**
     * ☆计算并返回灾煞【5】
     *
     * @return 四柱神煞：灾煞
     */
    private List<String> zaiSha() {

        /*
            【灾煞】算法↓

                1、年支为子，并且其他地支有'午'的，则为灾煞。
                2、年支为丑，并且其他地支有'卯'的，则为灾煞。
                3、年支为寅，并且其他地支有'子'的，则为灾煞。
                4、年支为卯，并且其他地支有'酉'的，则为灾煞。
                5、年支为辰，并且其他地支有'午'的，则为灾煞。
                6、年支为巳，并且其他地支有'卯'的，则为灾煞。
                7、年支为午，并且其他地支有'子'的，则为灾煞。
                8、年支为未，并且其他地支有'酉'的，则为灾煞。
                9、年支为申，并且其他地支有'午'的，则为灾煞。
                10、年支为酉，并且其他地支有'卯'的，则为灾煞。
                11、年支为戌，并且其他地支有'子'的，则为灾煞。
                12、年支为亥，并且其他地支有'酉'的，则为灾煞。
         */

        List<String> list = CommonUtil.addNullList(4);

        String _zaiShaZhi = BaZiMap.ZAI_SHA.get(getYearZhi()); // 根据年支获取灾煞落入的地支

        // 添加神煞
        saveShenSha(list, _zaiShaZhi, Constant.ZAI_SHA);

        return list;

    }

    /**
     * ☆计算并返回孤辰【5】
     *
     * @return 四柱神煞：孤辰
     */
    private List<String> guChen() {

        /*
            【孤辰】算法↓

                1、年支为子，并且其他地支有'寅'的，则为孤辰。
                2、年支为丑，并且其他地支有'寅'的，则为孤辰。
                3、年支为寅，并且其他地支有'巳'的，则为孤辰。
                4、年支为卯，并且其他地支有'巳'的，则为孤辰。
                5、年支为辰，并且其他地支有'巳'的，则为孤辰。
                6、年支为巳，并且其他地支有'申'的，则为孤辰。
                7、年支为午，并且其他地支有'申'的，则为孤辰。
                8、年支为未，并且其他地支有'申'的，则为孤辰。
                9、年支为申，并且其他地支有'亥'的，则为孤辰。
                10、年支为酉，并且其他地支有'亥'的，则为孤辰。
                11、年支为戌，并且其他地支有'亥'的，则为孤辰。
                12、年支为亥，并且其他地支有'寅'的，则为孤辰。
         */

        List<String> list = CommonUtil.addNullList(4);

        String _guChenYearZhi = BaZiMap.GU_CHEN.get(getYearZhi()); // 根据年支获取孤辰落入的地支

        // 添加神煞
        saveShenSha(list, _guChenYearZhi, Constant.GU_CHEN);

        return list;

    }

    /**
     * ☆计算并返回寡宿【5】
     *
     * @return 四柱神煞：寡宿
     */
    private List<String> suGua() {

        /*
            【寡宿】算法↓

                1、年支为子，并且其他地支有'戌'的，则为寡宿。
                2、年支为丑，并且其他地支有'戌'的，则为寡宿。
                3、年支为寅，并且其他地支有'丑'的，则为寡宿。
                4、年支为卯，并且其他地支有'丑'的，则为寡宿。
                5、年支为辰，并且其他地支有'丑'的，则为寡宿。
                6、年支为巳，并且其他地支有'辰'的，则为寡宿。
                7、年支为午，并且其他地支有'辰'的，则为寡宿。
                8、年支为未，并且其他地支有'辰'的，则为寡宿。
                9、年支为申，并且其他地支有'未'的，则为寡宿。
                10、年支为酉，并且其他地支有'未'的，则为寡宿。
                11、年支为戌，并且其他地支有'未'的，则为寡宿。
                12、年支为亥，并且其他地支有'戌'的，则为寡宿。
         */

        List<String> list = CommonUtil.addNullList(4);

        String _suGuaYearZhi = BaZiMap.SU_GUA.get(getYearZhi()); // 根据年支获取寡宿落入的地支

        // 添加神煞
        saveShenSha(list, _suGuaYearZhi, Constant.SU_GUA);

        return list;

    }

    /**
     * ☆计算并返回禄神【5】
     *
     * @return 四柱神煞：禄神
     */
    private List<String> luShen() {

        /*
            【禄神】算法↓

                1、日干为甲，并且其他地支有'寅'的，则为禄神。
                2、日干为乙，并且其他地支有'卯'的，则为禄神。
                3、日干为丙，并且其他地支有'巳'的，则为禄神。
                4、日干为丁，并且其他地支有'午'的，则为禄神。
                5、日干为戊，并且其他地支有'巳'的，则为禄神。
                6、日干为己，并且其他地支有'午'的，则为禄神。
                7、日干为庚，并且其他地支有'申'的，则为禄神。
                8、日干为辛，并且其他地支有'酉'的，则为禄神。
                9、日干为壬，并且其他地支有'亥'的，则为禄神。
                10、日干为癸，并且其他地支有'子'的，则为禄神。
         */

        List<String> list = CommonUtil.addNullList(4);

        String _luShenDayZhi = BaZiMap.LU_SHEN.get(getDayGan()); // 根据日干获取禄神落入的地支

        // 添加神煞
        saveShenSha(list, _luShenDayZhi, Constant.LU_SHEN);

        return list;

    }

//----------------------------------------------------------------------------------------------------------------------------------------------------

    /**
     * 返回加分
     *
     * @param shengKe   天干和天干五行生克关系 或 天干和地支五行生克关系
     * @param ganOrZhi1 天干或地支
     * @param ganOrZhi2 天干或地支
     * @param jia       加分
     * @return 加分
     */
    private int jiaFen(Map<List<String>, List<String>> shengKe, String ganOrZhi1, String ganOrZhi2, int jia) {

        int fen = 0;

        List<String> list = Arrays.asList(ganOrZhi1, ganOrZhi2);
        String qiangOrRuo = shengKe.get(list).get(0); // '强' 或 '弱'
        // 若身强则加分
        if (Constant.QIANG.equals(qiangOrRuo)) {
            fen += jia;
        }

        return fen;

    }

    /**
     * 返回身体强弱
     *
     * @param shengKe   天干和天干五行生克关系 或 天干和地支五行生克关系
     * @param ganOrZhi1 天干或地支
     * @param ganOrZhi2 天干或地支
     * @return true:强   false:弱
     */
    private boolean qiangOrRuo(Map<List<String>, List<String>> shengKe, String ganOrZhi1, String ganOrZhi2) {

        List<String> list = Arrays.asList(ganOrZhi1, ganOrZhi2);
        String qiangOrRuo = shengKe.get(list).get(0); // '强' 或 '弱'
        return Constant.QIANG.equals(qiangOrRuo);

    }

    /**
     * ★添加神煞
     *
     * @param allList 四柱神煞
     * @param yearS   保存年柱神煞
     * @param monthS  保存月柱神煞
     * @param dayS    保存日柱神煞
     * @param hourS   保存时柱神煞
     */
    private void saveShenShaZhi(List<String> allList, List<String> yearS, List<String> monthS, List<String> dayS, List<String> hourS) {

        try {
            yearS.add(allList.get(0)); // 年柱神煞
            monthS.add(allList.get(1)); // 月柱神煞
            dayS.add(allList.get(2)); // 日柱神煞
            hourS.add(allList.get(3)); // 时柱神煞
        } catch (Exception e) {
            throw new NullPointerException("神煞添加失败");
        }

    }

    /**
     * ☆添加神煞（适用于：太极贵人、天乙贵人、福星贵人）【1】
     *
     * @param siZhuShenSha 四柱神煞
     * @param ganZhi       天干或地支
     * @param ganOrZhi1    天干或地支
     * @param ganOrZhi2    天干或地支
     * @param index        所要插入数据的索引
     * @param shenShaName  神煞名称
     */
    private void saveShenSha(List<String> siZhuShenSha, String ganZhi, List<String> ganOrZhi1, List<String> ganOrZhi2, int index, String shenShaName) {

        for (String s : ganOrZhi1) {
            if (ganZhi.equals(s)) {
                siZhuShenSha.set(index, shenShaName);
                return;
            }
        }

        for (String s : ganOrZhi2) {
            if (ganZhi.equals(s)) {
                siZhuShenSha.set(index, shenShaName);
                return;
            }
        }

    }

    /**
     * ☆添加神煞（适用于：文昌贵人、天厨贵人、国印、驿马、华盖、劫煞、将星、桃花、亡神、丧门、吊客、披麻）【2】
     *
     * @param allList         四柱神煞
     * @param shenShaGanToZhi 根据年干获取神煞落入的地支
     * @param shenShaZhiToZhi 根据日干获取神煞落入的地支
     * @param shenShaName     神煞名称
     */
    private void saveShenSha(List<String> allList, String shenShaGanToZhi, String shenShaZhiToZhi, String shenShaName) {

        // 1、判断年柱
        if (getYearZhi().equals(shenShaGanToZhi) || getYearZhi().equals(shenShaZhiToZhi)) {
            allList.set(0, shenShaName);
        }

        // 2、判断月柱
        if (getMonthZhi().equals(shenShaGanToZhi) || getMonthZhi().equals(shenShaZhiToZhi)) {
            allList.set(1, shenShaName);
        }

        // 3、判断日柱
        if (getDayZhi().equals(shenShaGanToZhi) || getDayZhi().equals(shenShaZhiToZhi)) {
            allList.set(2, shenShaName);
        }

        // 4、判断时柱
        if (getHourZhi().equals(shenShaGanToZhi) || getHourZhi().equals(shenShaZhiToZhi)) {
            allList.set(3, shenShaName);
        }

    }

    /**
     * ☆添加神煞（适用于：阴差阳错、十恶大败、孤鸾煞、魁罡、八专、九丑、十灵、六秀）【3】
     *
     * @param allList     四柱神煞
     * @param ganOrZhi    天干或地支
     * @param shenSha     神煞数组
     * @param shenShaName 神煞名称
     */
    private void saveShenSha(List<String> allList, String ganOrZhi, String[] shenSha, String shenShaName) {

        for (String s : shenSha) {
            if (ganOrZhi.equals(s)) {
                allList.set(2, shenShaName); // 添加日柱神煞
            }
        }

    }

    /**
     * ☆添加神煞（适用于：学堂、词馆）【4-1：禄命法】
     *
     * @param allList        四柱神煞
     * @param yearMingWuXing 年命五行
     * @param wuXing         五行
     * @param Zhi            月支或日支或时支
     * @param shenShaName    神煞名称
     */
    private void saveShenSha(List<String> allList, String yearMingWuXing, String wuXing, String Zhi, String shenShaName) {

        if (wuXing.equals(yearMingWuXing)) {
            if (getMonthZhi().equals(Zhi)) allList.set(1, shenShaName); // 添加月柱神煞
            if (getDayZhi().equals(Zhi)) allList.set(2, shenShaName); // 添加日柱神煞
            if (getHourZhi().equals(Zhi)) allList.set(3, shenShaName); // 添加时柱神煞
        }

    }

    /**
     * ☆添加神煞（适用于：学堂、词馆）【4-2：子平法】
     *
     * @param allList     四柱神煞
     * @param ganOrZhi    天干或地支
     * @param shenShaName 神煞名称
     */
    private void saveShenSha(List<String> allList, List<String> ganOrZhi, String shenShaName) {

        for (String s : ganOrZhi) {
            if (getYearGan().equals(s) || getYearZhi().equals(s)) {
                allList.set(0, shenShaName); // 添加年柱神煞
            }
            if (getMonthGan().equals(s) || getMonthZhi().equals(s)) {
                allList.set(1, shenShaName); // 添加月柱神煞
            }
            if (getDayGan().equals(s) || getDayZhi().equals(s)) {
                allList.set(2, shenShaName); // 添加日柱神煞
            }
            if (getHourGan().equals(s) || getHourZhi().equals(s)) {
                allList.set(3, shenShaName); // 添加时柱神煞
            }
        }

    }

    /**
     * ☆添加神煞（适用于：红艳煞、金舆、羊刃、飞刃、血刃、流霞、天医、天喜、红鸾、灾煞、孤辰、寡宿、禄神）【5】
     *
     * @param allList         四柱神煞
     * @param shenShaGanToZhi 根据年干获取神煞落入的地支
     * @param shenShaName     神煞名称
     */
    private void saveShenSha(List<String> allList, String shenShaGanToZhi, String shenShaName) {

        // 1、判断年柱是否为神煞
        if (getYearZhi().equals(shenShaGanToZhi)) {
            allList.set(0, shenShaName);
        }

        // 2、判断月柱是否为神煞
        if (getMonthZhi().equals(shenShaGanToZhi)) {
            allList.set(1, shenShaName);
        }

        // 3、判断日柱是否为神煞
        if (getDayZhi().equals(shenShaGanToZhi)) {
            allList.set(2, shenShaName);
        }

        // 4、判断时柱是否为神煞
        if (getHourZhi().equals(shenShaGanToZhi)) {
            allList.set(3, shenShaName);
        }

    }

    @Override
    public String toString() {

        StringBuilder s = new StringBuilder();
        s.append("公历").append(getSolarStr());
        s.append("   ");
        s.append("农历").append(getLunarStr());
        s.append("   ");
        s.append("星期:").append(getWeek());
        s.append("   ");
        s.append("八字:").append(getBaZi());
        s.append("   ");
        s.append("八字五行:").append(getBaZiWuXing());
        s.append("   ");
        s.append("八字纳音:").append(getBaZiNaYin());
        s.append("   ");
        s.append("八字空亡:").append(getBaZiKongWang());
        s.append("   ");
        s.append("年柱主星:").append(getYearZhuZhuXing());
        s.append("   ");
        s.append("月柱主星:").append(getMonthZhuZhuXing());
        s.append("   ");
        s.append("日柱主星:").append(getDayZhuZhuXing());
        s.append("   ");
        s.append("时柱主星:").append(getHourZhuZhuXing());
        s.append("   ");
        s.append("年支藏干:").append(getYearZhiCangGan());
        s.append("   ");
        s.append("月支藏干:").append(getMonthZhiCangGan());
        s.append("   ");
        s.append("日支藏干:").append(getDayZhiCangGan());
        s.append("   ");
        s.append("时支藏干:").append(getHourZhiCangGan());
        s.append("   ");
        s.append("年柱副星:").append(getYearZhuFuXing());
        s.append("   ");
        s.append("月柱副星:").append(getMonthZhuFuXing());
        s.append("   ");
        s.append("日柱副星:").append(getDayZhuFuXing());
        s.append("   ");
        s.append("时柱副星:").append(getHourZhuFuXing());
        s.append("   ");
        s.append("年支地势:").append(getYearZhuDiShi());
        s.append("   ");
        s.append("月支地势:").append(getMonthZhuDiShi());
        s.append("   ");
        s.append("日支地势:").append(getDayZhuDiShi());
        s.append("   ");
        s.append("时支地势:").append(getHourZhuDiShi());
        s.append("   ");
        s.append("胎元:").append(getTaiYuan());
        s.append("   ");
        s.append("胎息:").append(getTaiXi());
        s.append("   ");
        s.append("命宫:").append(getMingGong());
        s.append("   ");
        s.append("身宫:").append(getShenGong());
        s.append("   ");
        s.append("起运:").append(getQiYun());
        s.append("   ");
        s.append("身体强弱:").append(getBodyIntensity());
        s.append("   ");
        s.append("喜用神:").append(getXiYongShen());
        s.append("   ");
        s.append("喜用神方位:").append(getXiYongShenFangWei());

        return s.toString();

    }


}
